import assert from "node:assert/strict"; import { mkdirSync, mkdtempSync, readFileSync, rmSync, symlinkSync, writeFileSync, } from "node:fs"; import { tmpdir } from "node:os"; import path from "node:path"; import { afterEach, describe, it } from "vitest"; import { applyInitialization } from "../init.ts"; import { startupRuntimeNotice, startupRuntimeState, } from "../startup-notice.ts"; import { CORE_BYTE_LIMIT, composeSystemSection, preflightFileMutation, runtimeNotice, runtimeState, } from "../system.ts"; const roots: string[] = []; const root = () => { const value = mkdtempSync(path.join(tmpdir(), "the-system-runtime-")); roots.push(value); applyInitialization(value, "PX"); for (const name of ["SYSTEM.md", "MISSION.md", "RULES.md"]) write(value, `.system/${name}`, `# ${name}\n\nApproved.\n`); return value; }; const write = (root: string, relative: string, content: string) => { const target = path.join(root, relative); mkdirSync(path.dirname(target), { recursive: true }); writeFileSync(target, content, "utf8"); }; const documentSource = (metadata: Record) => `---\n${Object.entries(metadata) .map( ([key, value]) => `${key}: ${Array.isArray(value) ? `[${value.join(", ")}]` : value}`, ) .join("\n")}\n---\n\n# Contract\n\nApproved.\n`; const specMetadata = { id: "PX-SPEC-SPEC0001", type: "spec", title: "Contract", }; const writeSpec = (project: string) => { const relative = ".system/specs/PX-SPEC-SPEC0001-contract/index.md"; write(project, relative, documentSource(specMetadata)); return relative; }; const approval = (hasUI = true) => ({ hasUI, select: async (_title: string, items: string[]) => items[0], }); afterEach(() => { for (const value of roots.splice(0)) rmSync(value, { recursive: true, force: true }); }); describe("runtime notice", () => { it("stays quiet until the project opts into .system", async () => { const project = mkdtempSync(path.join(tmpdir(), "the-system-runtime-")); roots.push(project); assert.deepEqual(runtimeState(project), { active: false }); assert.deepEqual(await startupRuntimeState(project), { active: false }); assert.equal(runtimeNotice(project), undefined); assert.equal(await startupRuntimeNotice(project), undefined); mkdirSync(path.join(project, ".system")); assert.deepEqual(runtimeState(project), { active: true, notice: "The System is incomplete or invalid; run /system init before governed work.", }); assert.match( (await startupRuntimeState(project)).notice ?? "", /incomplete or invalid/, ); assert.match(runtimeNotice(project) ?? "", /incomplete or invalid/); assert.match( (await startupRuntimeNotice(project)) ?? "", /incomplete or invalid/, ); }); it("reports the active project prefix", async () => { const project = root(); assert.deepEqual(runtimeState(project), { active: true, prefix: "PX" }); assert.deepEqual(await startupRuntimeState(project), { active: true, prefix: "PX", }); }); }); describe("runtime core injection", () => { it("injects the current phase after MISSION without mutating it", async () => { const project = root(); const phase = ".system/phases/PX-PHASE-PHASE001-pre-v1/index.md"; write( project, phase, documentSource({ id: "PX-PHASE-PHASE001", type: "phase", title: "Pre-v1", label: "pre-v1", }), ); const configPath = path.join(project, ".system/config.json"); const config = JSON.parse(readFileSync(configPath, "utf8")); writeFileSync( configPath, `${JSON.stringify({ ...config, currentPhase: "PX-PHASE-PHASE001" })}\n`, ); const missionPath = path.join(project, ".system/MISSION.md"); const mission = readFileSync(missionPath, "utf8"); const prompt = composeSystemSection(project) ?? ""; assert.match( prompt, /SYSTEM\.md[\s\S]*MISSION\.md[\s\S]*Current phase: Pre-v1 · pre-v1[\s\S]*RULES\.md/, ); assert.equal(readFileSync(missionPath, "utf8"), mission); assert.deepEqual(runtimeState(project), { active: true, prefix: "PX", phaseLabel: "pre-v1", }); assert.deepEqual(await startupRuntimeState(project), { active: true, prefix: "PX", phaseLabel: "pre-v1", }); rmSync(path.join(project, path.dirname(phase)), { recursive: true, force: true, }); assert.match(composeSystemSection(project) ?? "", /governance error/); }); it("injects cores and reports malformed core paths", () => { const project = root(); write(project, ".system/MISSION.md", "x".repeat(CORE_BYTE_LIMIT + 1)); assert.match(composeSystemSection(project) ?? "", /MISSION\.md exceeds/); rmSync(path.join(project, ".system/SYSTEM.md")); mkdirSync(path.join(project, ".system/SYSTEM.md")); assert.match(composeSystemSection(project) ?? "", /governance error/); }); }); describe("runtime bundle governance", () => { it("requires one-shot approval for each existing core mutation", async () => { const project = root(); const input = { path: "./.system/SYSTEM.md", edits: [{ oldText: "Approved.", newText: "Human-approved." }], }; let approvals = 0; const ui = { hasUI: true, select: async (title: string, items: string[]) => { approvals += 1; assert.equal(title, "The System ownership approval"); assert.deepEqual(items, [ "Approve once: edit .system/SYSTEM.md", "Deny: keep .system/SYSTEM.md unchanged", ]); return items[0]; }, }; assert.equal( await preflightFileMutation(project, "edit", input, ui), undefined, ); assert.equal( await preflightFileMutation(project, "edit", input, ui), undefined, ); assert.equal(approvals, 2); for (const [decision, message] of [ ["deny", /denied/], ["cancel", /cancelled/], ] as const) { const result = await preflightFileMutation(project, "edit", input, { hasUI: true, select: async (_title, items) => decision === "deny" ? items[1] : undefined, }); assert.equal(result?.block, true); assert.match(result?.reason ?? "", message); } const unavailable = await preflightFileMutation( project, "edit", input, approval(false), ); assert.equal(unavailable?.block, true); assert.match(unavailable?.reason ?? "", /interactive UI/); const oversized = await preflightFileMutation( project, "write", { path: ".system/SYSTEM.md", content: "x".repeat(CORE_BYTE_LIMIT + 1) }, { hasUI: true, select: async () => { throw new Error("unexpected approval"); }, }, ); assert.equal(oversized?.block, true); assert.match(oversized?.reason ?? "", /core limit/); }); it("activates an existing phase only after confirmation", async () => { const project = root(); write( project, ".system/phases/PX-PHASE-PHASE001-pre-v1/index.md", documentSource({ id: "PX-PHASE-PHASE001", type: "phase", title: "Pre-v1", label: "pre-v1", }), ); const configPath = path.join(project, ".system/config.json"); const config = JSON.parse(readFileSync(configPath, "utf8")); const candidate = `${JSON.stringify({ ...config, currentPhase: "PX-PHASE-PHASE001" })}\n`; let approvals = 0; const result = await preflightFileMutation( project, "write", { path: ".system/config.json", content: candidate }, { hasUI: true, select: async (_title, items) => { approvals += 1; assert.match(items[0] ?? "", /pre-v1 · Pre-v1/); return items[0]; }, }, ); assert.equal(result?.block, undefined); assert.equal(approvals, 1); const unavailable = await preflightFileMutation( project, "write", { path: ".system/config.json", content: candidate }, approval(false), ); assert.equal(unavailable?.block, true); assert.match(unavailable?.reason ?? "", /interactive UI/); for (const [decision, message] of [ ["deny", /denied/], ["cancel", /cancelled/], ] as const) { const rejected = await preflightFileMutation( project, "write", { path: ".system/config.json", content: candidate }, { hasUI: true, select: async (_title, items) => decision === "deny" ? items[1] : undefined, }, ); assert.equal(rejected?.block, true); assert.match(rejected?.reason ?? "", message); } writeFileSync(configPath, candidate); let deactivations = 0; const deactivated = await preflightFileMutation( project, "write", { path: ".system/config.json", content: `${JSON.stringify(config)}\n`, }, { hasUI: true, select: async (_title, items) => { deactivations += 1; assert.equal(items[0], "Deactivate current phase"); return items[0]; }, }, ); assert.equal(deactivated?.block, undefined); assert.equal(deactivations, 1); const unrelated = await preflightFileMutation( project, "write", { path: ".system/config.json", content: `${JSON.stringify({ ...config, title: "Changed", currentPhase: "PX-PHASE-PHASE001" })}\n`, }, approval(), ); assert.equal(unrelated?.block, true); assert.match(unrelated?.reason ?? "", /only change currentPhase/); }); it("reports rejected schema edits as config changes", async () => { const project = root(); const config = ".system/config.json"; write(project, config, '{"prefix":"PX","schemaVersion":1}\n'); const result = await preflightFileMutation( project, "edit", { path: config, edits: [{ oldText: '"schemaVersion":1', newText: '"schemaVersion":0' }], }, approval(), ); assert.equal(result?.block, true); assert.match(result?.reason ?? "", /rejected the config change/); assert.doesNotMatch(result?.reason ?? "", /phase change/); }); it("allows approved repair of invalid phase metadata", async () => { const project = root(); const phase = ".system/phases/PX-PHASE-PHASE001-pre-v1/index.md"; write( project, phase, "---\nid: PX-PHASE-PHASE001\ntype: phase\ntitle: Pre-v1\nspec: PX-SPEC-SPEC0001\nstatus: approved\n---\n", ); let approvals = 0; const result = await preflightFileMutation( project, "write", { path: phase, content: "---\nid: PX-PHASE-PHASE001\ntype: phase\ntitle: Pre-v1\nlabel: pre-v1\n---\n", }, { hasUI: true, select: async (_title, items) => { approvals += 1; return items[0]; }, }, ); assert.equal(result?.block, undefined); assert.equal(approvals, 1); }); it("allows scoped bundle migration without per-bundle approval", async () => { const project = root(); const phase = ".system/phases/PX-PHASE-PHASE001-pre-v1/index.md"; write( project, phase, "---\nid: PX-PHASE-PHASE001\ntype: phase\ntitle: Pre-v1\nspec: PX-SPEC-SPEC0001\nstatus: approved\n---\n", ); const migrated = await preflightFileMutation( project, "write", { path: phase, content: "---\nid: PX-PHASE-PHASE001\ntype: phase\ntitle: Pre-v1\nlabel: pre-v1\n---\n", }, approval(false), { bundleMigration: true }, ); assert.equal(migrated?.block, undefined); const invalid = await preflightFileMutation( project, "write", { path: phase, content: "---\nid: wrong\n---\n" }, approval(false), { bundleMigration: true }, ); assert.equal(invalid?.block, true); assert.match(invalid?.reason ?? "", /candidate validation failed/); }); it("does not govern mutations outside the detected project root", async () => { const project = root(); const outside = path.join(path.dirname(project), "outside.md"); assert.equal( ( await preflightFileMutation( project, "write", { path: outside, content: "outside" }, approval(), ) )?.block, undefined, ); }); it("allows valid new index candidates and blocks invalid layouts and metadata before approval", async () => { const project = root(); assert.equal( ( await preflightFileMutation( project, "write", { path: ".system/specs/PX-SPEC-SPEC0001-contract/index.md", content: documentSource(specMetadata), }, approval(), ) )?.block, undefined, ); for (const input of [ { path: ".system/spec/PX-SPEC-SPEC0002-broken/index.md", content: documentSource({ id: "PX-SPEC-SPEC0002", type: "spec", title: "Wrong directory", }), }, { path: ".system/specs/PX-SPEC-SPEC0002-broken/index.md", content: "# no frontmatter", }, { path: ".system/specs/PX-SPEC-SPEC0002-broken.md", content: "# loose document", }, { path: ".system/specs/loose.md", content: "x" }, { path: ".system/specs/PX-SPEC-SPEC0002-broken/other/index.md", content: "x", }, ]) { const result = await preflightFileMutation( project, "write", input, approval(), ); assert.equal(result?.block, true, input.path); assert.match(result?.reason ?? "", /bundle|candidate validation/i); } }); it("requires a valid index before assets and approves every existing spec file", async () => { const project = root(); const asset = ".system/specs/PX-SPEC-SPEC0001-contract/evidence/data.csv"; assert.equal( ( await preflightFileMutation( project, "write", { path: asset, content: "a,b" }, approval(), ) )?.block, true, ); const index = writeSpec(project); assert.equal( ( await preflightFileMutation( project, "write", { path: asset, content: "a,b" }, approval(), ) )?.block, undefined, ); for (const relative of [ index, ".system/specs/PX-SPEC-SPEC0001-contract/mockup-mobile.html", asset, ]) { write( project, relative, relative === index ? documentSource(specMetadata) : "existing", ); let approvals = 0; const result = await preflightFileMutation( project, "write", { path: relative, content: relative === index ? documentSource(specMetadata) : "replacement", }, { hasUI: true, select: async (_title, items) => { approvals += 1; return items[0]; }, }, ); assert.equal(result?.block, undefined, relative); assert.equal(approvals, 1, relative); } const closed = await preflightFileMutation( project, "write", { path: asset, content: "replacement" }, approval(false), ); assert.equal(closed?.block, true); assert.match(closed?.reason ?? "", /interactive UI/); }); it("approves phase amendments and keeps approved plans immutable", async () => { const project = root(); writeSpec(project); const phase = ".system/phases/PX-PHASE-PHASE001-delivery/index.md"; const plan = ".system/plans/PX-PLAN-PLAN0001-build/index.md"; const issue = ".system/issues/PX-ISSUE-ISSUE001-bug/index.md"; write( project, phase, documentSource({ id: "PX-PHASE-PHASE001", type: "phase", title: "Delivery", label: "delivery", }), ); write( project, plan, documentSource({ id: "PX-PLAN-PLAN0001", type: "plan", title: "Build", spec: "PX-SPEC-SPEC0001", status: "approved", }), ); write( project, issue, documentSource({ id: "PX-ISSUE-ISSUE001", type: "issue", title: "Bug", specs: ["PX-SPEC-SPEC0001"], }), ); let phaseApprovals = 0; const phaseResult = await preflightFileMutation( project, "edit", { path: phase, edits: [{ oldText: "Approved.", newText: "Reviewed." }], }, { hasUI: true, select: async (_title, items) => { phaseApprovals += 1; return items[0]; }, }, ); assert.equal(phaseResult?.block, undefined); assert.equal(phaseApprovals, 1); for (const target of [plan, plan.replace("index.md", "evidence.txt")]) { const result = await preflightFileMutation( project, target === plan ? "edit" : "write", target === plan ? { path: target, edits: [{ oldText: "Approved.", newText: "Reviewed." }], } : { path: target, content: "new" }, approval(), ); assert.equal(result?.block, true, target); assert.match(result?.reason ?? "", /approved/); } const draftPlan = ".system/plans/PX-PLAN-PLAN0002-draft/index.md"; write( project, draftPlan, documentSource({ id: "PX-PLAN-PLAN0002", type: "plan", title: "Draft plan", spec: "PX-SPEC-SPEC0001", status: "draft", }), ); let approvals = 0; const approvalResult = await preflightFileMutation( project, "edit", { path: draftPlan, edits: [{ oldText: "status: draft", newText: "status: approved" }], }, { hasUI: true, select: async (_title, items) => { approvals += 1; return items[0]; }, }, ); assert.equal(approvalResult?.block, undefined); assert.equal(approvals, 1); const issueResult = await preflightFileMutation( project, "edit", { path: issue, edits: [{ oldText: "Approved.", newText: "Reviewed." }] }, { hasUI: true, select: async () => { throw new Error("unexpected approval"); }, }, ); assert.equal(issueResult?.block, undefined); }); it("validates computed edits before approval and rejects symlinks", async () => { const project = root(); const relative = writeSpec(project); const result = await preflightFileMutation( project, "edit", { path: relative, edits: [ { oldText: "id: PX-SPEC-SPEC0001", newText: "id: PX-SPEC-SPEC0002" }, ], }, approval(), ); assert.equal(result?.block, true); assert.match(result?.reason ?? "", /candidate validation/i); symlinkSync( "missing.md", path.join(project, ".system/specs/PX-SPEC-SPEC0002-link"), ); const linked = await preflightFileMutation( project, "write", { path: ".system/specs/PX-SPEC-SPEC0002-link/index.md", content: documentSource({ id: "PX-SPEC-SPEC0002", type: "spec", title: "Link", }), }, approval(), ); assert.equal(linked?.block, true); assert.match(linked?.reason ?? "", /symbolic link/i); }); });