import assert from "node:assert/strict" import { existsSync, mkdtempSync, mkdirSync, readFileSync, rmSync, writeFileSync } from "node:fs" import { tmpdir } from "node:os" import path from "node:path" import { test } from "node:test" import { fileURLToPath } from "node:url" import { buildSkills, loadClassification, renderMatrix, updateDocMatrix, type ClassificationEntry, } from "../scripts/generate.ts" import { isUserInvoked, parseFrontmatter } from "../scripts/frontmatter.ts" const root = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "..") test("parseFrontmatter: plain, quoted with escapes and colons, DMI, nested blocks skipped", () => { const plain = parseFrontmatter("---\nname: tdd\ndescription: Test-driven development\n---\nBody\n") assert.equal(plain.frontmatter.name, "tdd") assert.equal(plain.frontmatter.description, "Test-driven development") assert.equal(plain.body, "Body\n") const quoted = parseFrontmatter( '---\nname: code-review\ndescription: "Review since a fixed point: commit, branch, or \\"X\\"."\nmetadata:\n credits:\n author: Dex\n---\nx', ) assert.equal( quoted.frontmatter.description, 'Review since a fixed point: commit, branch, or "X".', ) assert.equal(quoted.frontmatter.metadata, "") // nested block skipped, not misparsed const dmi = parseFrontmatter("---\nname: to-spec\ndisable-model-invocation: true\n---\nx") assert.equal(isUserInvoked(dmi.frontmatter), true) assert.equal(isUserInvoked(plain.frontmatter), false) const none = parseFrontmatter("no frontmatter here") assert.deepEqual(none.frontmatter, {}) }) function fixtureSkill(upstream: string, bucket: string, name: string, opts: { dmi?: boolean } = {}) { const dir = path.join(upstream, bucket, name) mkdirSync(path.join(dir, "agents"), { recursive: true }) writeFileSync( path.join(dir, "SKILL.md"), `---\nname: ${name}\ndescription: "The ${name} skill"\n` + (opts.dmi ? "disable-model-invocation: true\n" : "") + `---\n\nBody of ${name}.\n`, ) writeFileSync(path.join(dir, "agents", "openai.yaml"), "interface:\n display_name: X\n") writeFileSync(path.join(dir, "EXTRA.md"), "supporting file") return dir } function entry(name: string, bucket: string, over: Partial = {}) { return { name, bucket, classification: "skill", user_invoked: false, artifacts: ["skill:verbatim"], depends_on: [], status: "analyzed", rationale: "r", ...over, } as ClassificationEntry } test("buildSkills copies verbatim minus agents/, builds manifest, honors exclusions", () => { const dir = mkdtempSync(path.join(tmpdir(), "gen-test-")) try { const upstream = path.join(dir, "upstream") fixtureSkill(upstream, "engineering", "tdd") fixtureSkill(upstream, "engineering", "to-spec", { dmi: true }) fixtureSkill(upstream, "in-progress", "beta") const out = path.join(dir, "skills") const manifest = buildSkills({ upstreamSkills: upstream, entries: [entry("tdd", "engineering"), entry("to-spec", "engineering"), entry("beta", "in-progress", { artifacts: ["excluded"] })], skillsOut: out, }) assert.deepEqual( manifest, [ { id: "tdd", name: "tdd", description: "The tdd skill", autoinvoke: true, path: "skills/tdd/SKILL.md" }, { id: "to-spec", name: "to-spec", description: "The to-spec skill", autoinvoke: false, path: "skills/to-spec/SKILL.md" }, ].sort((a, b) => a.id.localeCompare(b.id)), ) assert.ok(existsSync(path.join(out, "tdd/SKILL.md"))) assert.ok(existsSync(path.join(out, "tdd/EXTRA.md")), "supporting files preserved") assert.ok(!existsSync(path.join(out, "tdd/agents")), "agents/openai.yaml stripped") assert.ok(!existsSync(path.join(out, "beta")), "excluded skill not copied") } finally { rmSync(dir, { recursive: true, force: true }) } }) test("buildSkills throws on unclassified upstream skills and missing classified ones", () => { const dir = mkdtempSync(path.join(tmpdir(), "gen-test-")) try { const upstream = path.join(dir, "upstream") fixtureSkill(upstream, "engineering", "mystery") assert.throws( () => buildSkills({ upstreamSkills: upstream, entries: [], skillsOut: path.join(dir, "out") }), /unclassified upstream skill: engineering\/mystery/, ) assert.throws( () => buildSkills({ upstreamSkills: upstream, entries: [entry("ghost", "engineering")], skillsOut: path.join(dir, "out"), }), /classified skill missing upstream: engineering\/ghost/, ) } finally { rmSync(dir, { recursive: true, force: true }) } }) test("updateDocMatrix replaces only the marked section", () => { const dir = mkdtempSync(path.join(tmpdir(), "gen-test-")) try { const doc = path.join(dir, "doc.md") writeFileSync(doc, "prose\n\nold\n\nmore prose\n") updateDocMatrix(doc, "NEW TABLE") assert.equal(readFileSync(doc, "utf8"), "prose\n\n\nNEW TABLE\n\n\nmore prose\n") assert.throws(() => updateDocMatrix(doc.replace("doc", "x"), "t"), /ENOENT/) writeFileSync(path.join(dir, "bad.md"), "no markers") assert.throws(() => updateDocMatrix(path.join(dir, "bad.md"), "t"), /missing matrix markers/) } finally { rmSync(dir, { recursive: true, force: true }) } }) test("renderMatrix: one row per entry with escaped cells", () => { const md = renderMatrix([entry("tdd", "engineering", { depends_on: ["codebase-design"], rationale: "a | b" })]) const [header, sep, row] = md.split("\n") assert.match(header, /^\| Upstream skill \| Bucket \| DMI \|/) assert.match(sep, /^\| --- \|/) assert.equal(row, "| tdd | eng | | skill | skill:verbatim | codebase-design | analyzed | a \\| b |") }) // Regression against the real vendored snapshot: every classified-verbatim skill must parse, // and upstream disable-model-invocation must agree with classification.json user_invoked. test("real snapshot: all vendored skills parse and DMI flags match classification", () => { const entries = loadClassification(path.join(root, ".opencode/state/classification.json")) const manifest = JSON.parse(readFileSync(path.join(root, "manifest.json"), "utf8")) const vendored = entries.filter((e) => e.artifacts.includes("skill:verbatim")) assert.equal(vendored.length, manifest.length) assert.equal(entries.filter((e) => e.status === "needs-review").length, 0) for (const e of vendored) { const md = readFileSync(path.join(root, "skills", e.name, "SKILL.md"), "utf8") const { frontmatter } = parseFrontmatter(md) assert.ok(frontmatter.name, `${e.name}: name parsed`) assert.ok(frontmatter.description, `${e.name}: description parsed`) assert.equal( isUserInvoked(frontmatter), e.user_invoked, `${e.name}: DMI flag disagrees with classification.json`, ) const m = manifest.find((x: { id: string }) => x.id === e.name) assert.equal(m.autoinvoke, !e.user_invoked, `${e.name}: manifest autoinvoke`) assert.ok(!existsSync(path.join(root, "skills", e.name, "agents")), `${e.name}: openai.yaml stripped`) } assert.equal(manifest.filter((m: { autoinvoke: boolean }) => !m.autoinvoke).length, 16) })