import { randomBytes } from "node:crypto"; import { mkdir, writeFile } from "node:fs/promises"; import { join } from "node:path"; import { createHermesCompositeManifest, HERMES_SPEC_REVIEW_STAGE_ID } from "./hermes-adapter.ts"; import { hashWorkflowRunLedger, type WorkflowRunStateLedger } from "./workflow-run-state.ts"; import type { WorkflowCatalogManifest } from "./workflow-catalog.ts"; import { PRODUCTION_PROJECT_ID, PRODUCTION_PROJECT_NAME, PRODUCTION_REPO_PATH, PRODUCTION_DAEMON_ID, PRODUCTION_WORKER_AGENT_ID, buildProductionBindingPlan, } from "./workflow-production-binding.ts"; import type { StageArtifactContentBuilder } from "./workflow-sandbox-campaign.ts"; export const PRODUCTION_CONTROLLER_AGENT_ID = "58af011a-8a45-4dba-bca9-4bde1a81ebe5"; export const PRODUCTION_STATE_RELATIVE = ".multica-spine/production-run-state.json"; export const PRODUCTION_ROUGH_IDEA = "Update pi-multica-spine README and ops docs for v0.5.0: document jsonl-digest CLI, sandbox canary, production binding, and production-run workflow scripts; verify npm install path for @0.5.0."; export interface ProductionRunPlan { projectId: string; projectName: string; repoPath: string; daemonId: string; controllerAgentId: string; workerAgentId: string; roughIdea: string; artifactRoot: string; deliveryPolicy: ReturnType["deliveryPolicy"]; } export function buildProductionRunPlan(repoPath = PRODUCTION_REPO_PATH): ProductionRunPlan { const bindingPlan = buildProductionBindingPlan(); return { projectId: PRODUCTION_PROJECT_ID, projectName: PRODUCTION_PROJECT_NAME, repoPath, daemonId: PRODUCTION_DAEMON_ID, controllerAgentId: PRODUCTION_CONTROLLER_AGENT_ID, workerAgentId: PRODUCTION_WORKER_AGENT_ID, roughIdea: PRODUCTION_ROUGH_IDEA, artifactRoot: bindingPlan.artifactRoot, deliveryPolicy: bindingPlan.deliveryPolicy, }; } export function buildProductionWorkflowRunId(now = new Date()): string { const date = now.toISOString().slice(0, 10).replace(/-/g, ""); return `prod-${date}-${randomBytes(4).toString("hex")}`; } function manifestStage(manifest: WorkflowCatalogManifest, stageId: string) { const stage = manifest.stages.find((item) => item.stageId === stageId); if (!stage) throw new Error(`Unknown manifest stage: ${stageId}`); return stage; } export const buildProductionStageArtifactContent: StageArtifactContentBuilder = ( stageId, manifest, ledger, roughIdea, ) => { const stage = manifestStage(manifest, stageId); const outputs = stage.outputs?.join(", ") ?? "artifact"; if (stageId === "implementation") { return [ "# Build report", "", "Documented v0.5.0 workflow operations in README and production binding docs.", "", "## Scripts", "- `scripts/jsonl-digest.mjs`", "- `scripts/workflow-sandbox-canary.mjs`", "- `scripts/workflow-production-binding.mjs`", "- `scripts/workflow-production-run.mjs`", "", "## Policy", "- color_output_policy=json_default_opt_in_color", `- rough_idea: ${roughIdea}`, ].join("\n"); } if (stageId === "question_resolution") { return [ "# Question resolution", "", "## Q1: Which workflow scripts ship in v0.5.0?", "- answer_status: observed", "- decision: README lists jsonl-digest, sandbox canary, production binding, production run", "- policy_key: production_ops_documentation", `- rough_idea: ${roughIdea}`, ].join("\n"); } if (stageId === HERMES_SPEC_REVIEW_STAGE_ID) { return [ "# Spec review", "", "Verdict: pass", "- README and docs cover production lane entrypoints", "- prRequired remains true on production binding", ].join("\n"); } if (stageId === "final_package") { return [ "# Final output package", "", `workflow_run_id: ${ledger.workflowRunId}`, `ledger_hash: ${hashWorkflowRunLedger(ledger)}`, "", "Deliverables: README v0.5.0 ops section + production workflow run evidence.", "Human final review requested.", ].join("\n"); } return [ `# ${stageId}`, "", `role: ${stage.role}`, `outputs: ${outputs}`, "", roughIdea, ].join("\n"); }; export async function writeProductionImplementationArtifacts(repoPath: string): Promise { const evidencePath = join(repoPath, "docs/investigations/2026-07-24-production-workflow-run-evidence.md"); await mkdir(join(repoPath, "docs/investigations"), { recursive: true }); const body = [ "# Production Workflow Run Evidence", "", "Generated by `workflow-production-run.mjs` implementation stage.", "", "## Scope", "- README v0.5.0 workflow operations section", "- Production binding + production run CLI documentation", "- JSON default / `--human` / `--color` policy", "", `generated_at: ${new Date().toISOString()}`, ].join("\n"); await writeFile(evidencePath, `${body}\n`, "utf8"); } export function productionFinalPackageDir(repoPath: string, workflowRunId: string): string { return join(repoPath, "Artifacts/workflows", workflowRunId, "final"); } export function productionReviewArtifactPath(repoPath: string, workflowRunId: string): string { return join(productionFinalPackageDir(repoPath, workflowRunId), "10-human-final-review.md"); } export function productionCampaignState(repoPath: string, state: { projectId: string; parentIssueId: string; workflowRunId: string; autopilotId?: string; }) { return { canaryPath: repoPath, projectId: state.projectId, parentIssueId: state.parentIssueId, workflowRunId: state.workflowRunId, autopilotId: state.autopilotId, }; } export function summarizeProductionLedger(ledger: WorkflowRunStateLedger | undefined) { if (!ledger) return undefined; return { workflowRunId: ledger.workflowRunId, workflowStatus: ledger.workflowStatus, currentStageId: ledger.currentStageId, ledgerHash: hashWorkflowRunLedger(ledger), stageCount: Object.keys(ledger.stages).length, }; }