Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,14 @@ jobs:
- name: TypeScript typecheck
run: bun run typecheck

- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.12'

- name: Install skills-ref (required by bun run validate for tier-1 spec checks)
run: pip install skills-ref==0.1.1

- name: Validate skill frontmatter
run: bun run validate

Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"description": "Claude Code skills for Bitcoin/Stacks blockchain operations — flat SKILL.md + colocated TypeScript CLI scripts.",
"type": "module",
"scripts": {
"build": "bun build src/lib/index.ts --outdir dist",
"build": "bun build src/lib/index.ts --outdir dist --target bun",
"typecheck": "tsc --noEmit",
"manifest": "bun run scripts/generate-manifest.ts",
"validate": "bun run scripts/validate-frontmatter.ts",
Expand Down
13 changes: 7 additions & 6 deletions scripts/validate-frontmatter.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,18 +10,19 @@ const repoRoot = dirname(scriptsDir);
// CLI flags
const skipSpec = process.argv.includes("--skip-spec");

// Find the skills-ref binary: prefer local venv, fall back to PATH
// Find the agentskills binary: prefer local venv, fall back to PATH
// Note: skills-ref PyPI package >= 0.1.1 installs the CLI as `agentskills` (renamed from `skills-ref`)
async function findSkillsRef(): Promise<string | null> {
const localBin = join(repoRoot, ".venv-skills-ref/bin/skills-ref");
const localBin = join(repoRoot, ".venv-skills-ref/bin/agentskills");
try {
const stat = await Bun.file(localBin).stat();
if (stat.size > 0) return localBin;
} catch {
// not found locally
}
// Fall back to PATH (cross-platform)
const pathResult = Bun.which("skills-ref");
if (pathResult) return "skills-ref";
const pathResult = Bun.which("agentskills");
if (pathResult) return "agentskills";
return null;
}

Expand Down Expand Up @@ -145,15 +146,15 @@ if (!skipSpec) {
skillsRefBin = await findSkillsRef();
if (skillsRefBin === null) {
process.stderr.write(
"WARNING: skills-ref not found. Skipping tier-1 spec validation. Install with: pip install skills-ref\n"
"WARNING: agentskills not found. Skipping tier-1 spec validation. Install with: pip install skills-ref\n"
);
}
}

// Print active tiers
const tier1Active = !skipSpec && skillsRefBin !== null;
console.log(
`Validation tiers: ${tier1Active ? "[tier-1: skills-ref]" : "[tier-1: SKIPPED]"} [tier-2: Zod]`
`Validation tiers: ${tier1Active ? "[tier-1: agentskills]" : "[tier-1: SKIPPED]"} [tier-2: Zod]`
);
console.log("");

Expand Down
Loading