@opengsd/gsd-core 1.11.0 → 1.13.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.claude-plugin/marketplace.json +1 -1
- package/.claude-plugin/plugin.json +1 -1
- package/.opencode/plugins/gsd-core.js +12 -0
- package/agents/gsd-code-fixer.md +1 -1
- package/agents/gsd-debug-session-manager.md +1 -1
- package/agents/gsd-debugger.md +1 -1
- package/agents/gsd-dom-verifier.md +169 -0
- package/agents/gsd-eval-auditor.md +1 -1
- package/agents/gsd-executor.md +78 -42
- package/agents/gsd-framework-selector.md +1 -3
- package/agents/gsd-intel-updater.md +1 -1
- package/agents/gsd-mempalace-curator.md +0 -1
- package/agents/gsd-pattern-mapper.md +11 -0
- package/agents/gsd-phase-researcher.md +3 -1
- package/agents/gsd-plan-checker.md +91 -112
- package/agents/gsd-planner.md +20 -4
- package/agents/gsd-project-researcher.md +1 -1
- package/agents/gsd-research-synthesizer.md +2 -2
- package/agents/gsd-roadmapper.md +15 -11
- package/agents/gsd-ui-checker.md +82 -7
- package/agents/gsd-ui-researcher.md +70 -3
- package/agents/gsd-verifier.md +24 -2
- package/bin/install.js +847 -200
- package/commands/gsd/discuss-phase.md +1 -1
- package/commands/gsd/execute-phase.md +1 -1
- package/commands/gsd/import.md +1 -1
- package/commands/gsd/ns-workflow.md +2 -1
- package/commands/gsd/phase.md +1 -1
- package/commands/gsd/quick-batch.md +105 -0
- package/commands/gsd/quick.md +8 -4
- package/commands/gsd/surface.md +18 -8
- package/gsd-core/bin/gsd-tools.cjs +761 -100
- package/gsd-core/bin/lib/active-workstream-store.cjs +8 -0
- package/gsd-core/bin/lib/adr-parser.cjs +13 -7
- package/gsd-core/bin/lib/agent-install-check.cjs +162 -0
- package/gsd-core/bin/lib/api-coverage.cjs +30 -9
- package/gsd-core/bin/lib/artifacts.cjs +2 -0
- package/gsd-core/bin/lib/assumption-delta.cjs +30 -11
- package/gsd-core/bin/lib/audit.cjs +163 -41
- package/gsd-core/bin/lib/broken-windows.cjs +306 -28
- package/gsd-core/bin/lib/capability-activation.cjs +27 -0
- package/gsd-core/bin/lib/capability-lock.cjs +10 -4
- package/gsd-core/bin/lib/capability-registry.cjs +785 -144
- package/gsd-core/bin/lib/capability-state.cjs +25 -4
- package/gsd-core/bin/lib/capability-validator.cjs +321 -18
- package/gsd-core/bin/lib/capability-writer.cjs +14 -4
- package/gsd-core/bin/lib/check-command-router.cjs +229 -6
- package/gsd-core/bin/lib/claude-orchestration.cjs +10 -25
- package/gsd-core/bin/lib/cli-exit.cjs +496 -10
- package/gsd-core/bin/lib/clusters.cjs +1 -0
- package/gsd-core/bin/lib/code-review-depth.cjs +288 -0
- package/gsd-core/bin/lib/codex-agent-toml.cjs +410 -4
- package/gsd-core/bin/lib/command-aliases.cjs +16 -0
- package/gsd-core/bin/lib/command-arg-projection.cjs +144 -14
- package/gsd-core/bin/lib/command-routing-hub.cjs +31 -2
- package/gsd-core/bin/lib/commands.cjs +877 -54
- package/gsd-core/bin/lib/complexity-trigger.cjs +26 -6
- package/gsd-core/bin/lib/config-loader.cjs +121 -29
- package/gsd-core/bin/lib/config.cjs +92 -2
- package/gsd-core/bin/lib/configuration.cjs +129 -37
- package/gsd-core/bin/lib/core-utils.cjs +118 -14
- package/gsd-core/bin/lib/decisions.cjs +213 -1
- package/gsd-core/bin/lib/edge-probe.cjs +23 -2
- package/gsd-core/bin/lib/estimate-cli.cjs +55 -11
- package/gsd-core/bin/lib/exit-code-registry.cjs +98 -0
- package/gsd-core/bin/lib/file-overlap-partitioner.cjs +74 -0
- package/gsd-core/bin/lib/frontmatter.cjs +975 -326
- package/gsd-core/bin/lib/gap-checker.cjs +41 -8
- package/gsd-core/bin/lib/git-base-branch.cjs +182 -39
- package/gsd-core/bin/lib/health-diagnostic-rules/consistency.cjs +7 -3
- package/gsd-core/bin/lib/health-diagnostic-rules/phase-structure.cjs +8 -2
- package/gsd-core/bin/lib/health-diagnostic-rules/roadmap-disk-consistency.cjs +60 -14
- package/gsd-core/bin/lib/health-diagnostic-rules/state-consistency.cjs +75 -22
- package/gsd-core/bin/lib/health-diagnostic-rules/worktree-health.cjs +22 -8
- package/gsd-core/bin/lib/health-diagnostic.cjs +23 -3
- package/gsd-core/bin/lib/host-integration.cjs +96 -11
- package/gsd-core/bin/lib/init-command-router.cjs +132 -21
- package/gsd-core/bin/lib/init.cjs +252 -56
- package/gsd-core/bin/lib/install-engine.cjs +252 -15
- package/gsd-core/bin/lib/install-model-override-resolver.cjs +78 -1
- package/gsd-core/bin/lib/install-profiles.cjs +100 -18
- package/gsd-core/bin/lib/installer-migration-report.cjs +4 -0
- package/gsd-core/bin/lib/installer-migrations/010-antigravity-retire-confighome-artifacts.cjs +169 -0
- package/gsd-core/bin/lib/installer-migrations.cjs +10 -7
- package/gsd-core/bin/lib/intel.cjs +101 -26
- package/gsd-core/bin/lib/io.cjs +195 -15
- package/gsd-core/bin/lib/learnings.cjs +85 -14
- package/gsd-core/bin/lib/legacy-cleanup.cjs +8 -2
- package/gsd-core/bin/lib/loop-resolver.cjs +14 -8
- package/gsd-core/bin/lib/markdown-table.cjs +175 -4
- package/gsd-core/bin/lib/milestone.cjs +112 -7
- package/gsd-core/bin/lib/model-catalog.cjs +177 -19
- package/gsd-core/bin/lib/model-resolver.cjs +10 -28
- package/gsd-core/bin/lib/onboard-projection.cjs +5 -1
- package/gsd-core/bin/lib/phase-command-router.cjs +13 -6
- package/gsd-core/bin/lib/phase-estimation.cjs +17 -8
- package/gsd-core/bin/lib/phase-id.cjs +321 -13
- package/gsd-core/bin/lib/phase-lifecycle.cjs +24 -16
- package/gsd-core/bin/lib/phase-locator.cjs +138 -17
- package/gsd-core/bin/lib/phase.cjs +1175 -115
- package/gsd-core/bin/lib/plan-document.cjs +273 -0
- package/gsd-core/bin/lib/plan-scan.cjs +13 -2
- package/gsd-core/bin/lib/planning-command-router.cjs +61 -0
- package/gsd-core/bin/lib/planning-inspect.cjs +1168 -0
- package/gsd-core/bin/lib/planning-snapshot.cjs +165 -34
- package/gsd-core/bin/lib/planning-workspace.cjs +159 -28
- package/gsd-core/bin/lib/probe-core.cjs +4 -1
- package/gsd-core/bin/lib/profile-pipeline-command-router.cjs +50 -7
- package/gsd-core/bin/lib/profile-pipeline.cjs +6 -3
- package/gsd-core/bin/lib/quick-batch-command-router.cjs +285 -0
- package/gsd-core/bin/lib/quick-batch-dispatch.cjs +250 -0
- package/gsd-core/bin/lib/quick-batch.cjs +840 -0
- package/gsd-core/bin/lib/real-home-guard.cjs +419 -0
- package/gsd-core/bin/lib/refactor-trigger-command-router.cjs +71 -45
- package/gsd-core/bin/lib/review-lane-descriptor.cjs +62 -14
- package/gsd-core/bin/lib/review-lane-invocation.cjs +73 -1
- package/gsd-core/bin/lib/review-lane-runner.cjs +136 -10
- package/gsd-core/bin/lib/roadmap-command-router.cjs +45 -31
- package/gsd-core/bin/lib/roadmap-parser.cjs +577 -41
- package/gsd-core/bin/lib/roadmap.cjs +248 -64
- package/gsd-core/bin/lib/runtime-artifact-conversion.cjs +329 -41
- package/gsd-core/bin/lib/runtime-artifact-install-plan.cjs +16 -17
- package/gsd-core/bin/lib/runtime-artifact-layout.cjs +320 -109
- package/gsd-core/bin/lib/runtime-hooks-surface.cjs +487 -83
- package/gsd-core/bin/lib/runtime-identity.cjs +234 -0
- package/gsd-core/bin/lib/runtime-slash.cjs +72 -2
- package/gsd-core/bin/lib/shell-command-projection.cjs +75 -8
- package/gsd-core/bin/lib/smart-entry.cjs +19 -31
- package/gsd-core/bin/lib/spec-section.cjs +12 -7
- package/gsd-core/bin/lib/state-command-router.cjs +47 -18
- package/gsd-core/bin/lib/state-contract.cjs +359 -0
- package/gsd-core/bin/lib/state-document.cjs +216 -5
- package/gsd-core/bin/lib/state-md-schema.cjs +231 -0
- package/gsd-core/bin/lib/state-transition.cjs +850 -145
- package/gsd-core/bin/lib/state.cjs +1629 -287
- package/gsd-core/bin/lib/surface.cjs +33 -10
- package/gsd-core/bin/lib/task-command-router.cjs +111 -1
- package/gsd-core/bin/lib/task-content-resolution.cjs +368 -0
- package/gsd-core/bin/lib/tdd-red-evidence.cjs +133 -0
- package/gsd-core/bin/lib/teams-status.cjs +4 -1
- package/gsd-core/bin/lib/uat-predicate.cjs +58 -20
- package/gsd-core/bin/lib/uat.cjs +2542 -387
- package/gsd-core/bin/lib/ui-consideration-probe.cjs +9 -1
- package/gsd-core/bin/lib/ui-safety-gate.cjs +37 -7
- package/gsd-core/bin/lib/unusable-input.cjs +13 -0
- package/gsd-core/bin/lib/update-context.cjs +6 -2
- package/gsd-core/bin/lib/validate-command-router.cjs +2 -2
- package/gsd-core/bin/lib/validate.cjs +230 -12
- package/gsd-core/bin/lib/vendor/README.md +43 -5
- package/gsd-core/bin/lib/vendor/js-yaml.cjs +3014 -0
- package/gsd-core/bin/lib/verification-command-router.cjs +2 -1
- package/gsd-core/bin/lib/verification.cjs +287 -13
- package/gsd-core/bin/lib/verify-command-grounding.cjs +846 -0
- package/gsd-core/bin/lib/verify-command-router.cjs +1 -0
- package/gsd-core/bin/lib/verify.cjs +441 -56
- package/gsd-core/bin/lib/workstream-inventory.cjs +20 -2
- package/gsd-core/bin/lib/workstream-name-policy.cjs +25 -4
- package/gsd-core/bin/lib/worktree-base-ref.cjs +66 -12
- package/gsd-core/bin/lib/worktree-safety.cjs +185 -21
- package/gsd-core/bin/shared/config-defaults.manifest.json +7 -1
- package/gsd-core/bin/shared/config-schema.manifest.json +13 -0
- package/gsd-core/bin/shared/exit-codes.json +8 -0
- package/gsd-core/bin/shared/exit-codes.sh +20 -0
- package/gsd-core/bin/shared/model-catalog.json +8 -1
- package/gsd-core/bin/verify-reapply-patches.cjs +70 -3
- package/gsd-core/references/agent-contracts.md +6 -5
- package/gsd-core/references/api-coverage.md +24 -2
- package/gsd-core/references/autonomous-smart-discuss.md +3 -3
- package/gsd-core/references/checkpoints.md +37 -19
- package/gsd-core/references/decimal-phase-calculation.md +5 -5
- package/gsd-core/references/edge-probe.md +17 -5
- package/gsd-core/references/execute-mvp-tdd.md +18 -18
- package/gsd-core/references/execute-phase-between-wave-reset.md +9 -12
- package/gsd-core/references/execute-phase-response-language.md +6 -0
- package/gsd-core/references/execute-phase-wave-guard.md +11 -9
- package/gsd-core/references/executor-examples.md +42 -0
- package/gsd-core/references/failing-direction.md +78 -0
- package/gsd-core/references/few-shot-examples/plan-checker.md +15 -15
- package/gsd-core/references/gate-prompts.md +1 -1
- package/gsd-core/references/git-integration.md +5 -5
- package/gsd-core/references/git-planning-commit.md +3 -3
- package/gsd-core/references/gsd-run-resolver.md +1 -1
- package/gsd-core/references/loop-hook-dispatch.md +22 -0
- package/gsd-core/references/model-profiles.md +1 -1
- package/gsd-core/references/mvp-concepts.md +2 -2
- package/gsd-core/references/nyquist-compliance.md +74 -0
- package/gsd-core/references/offer-next.md +3 -5
- package/gsd-core/references/phase-argument-parsing.md +3 -3
- package/gsd-core/references/plan-checker-examples.md +41 -0
- package/gsd-core/references/planner-antipatterns.md +25 -0
- package/gsd-core/references/planner-chunked.md +5 -1
- package/gsd-core/references/planner-coupling.md +42 -0
- package/gsd-core/references/planner-failing-direction.md +53 -0
- package/gsd-core/references/planner-human-verify-mode.md +15 -1
- package/gsd-core/references/planner-quick-batch.md +71 -0
- package/gsd-core/references/planner-reviews.md +47 -0
- package/gsd-core/references/planner-revision.md +76 -3
- package/gsd-core/references/planner-verify-command-grounding.md +17 -0
- package/gsd-core/references/planning-config.md +39 -9
- package/gsd-core/references/response-language-directive.md +9 -0
- package/gsd-core/references/reviewer-instances.md +31 -0
- package/gsd-core/references/revision-loop.md +118 -11
- package/gsd-core/references/runtime-aware-dispatch.md +1 -1
- package/gsd-core/references/tdd.md +15 -12
- package/gsd-core/references/ui-brand.md +65 -21
- package/gsd-core/references/ui-consideration-probe.md +1 -1
- package/gsd-core/references/universal-anti-patterns.md +2 -2
- package/gsd-core/references/verifier-evidence-gate.md +160 -0
- package/gsd-core/references/verify-command-path-resolvability.md +42 -0
- package/gsd-core/references/verify-mvp-mode.md +1 -1
- package/gsd-core/references/workstream-flag.md +11 -11
- package/gsd-core/templates/README.md +1 -1
- package/gsd-core/templates/SECURITY.md +3 -3
- package/gsd-core/templates/UI-SPEC.md +25 -3
- package/gsd-core/templates/VALIDATION.md +3 -3
- package/gsd-core/templates/phase-prompt.md +7 -0
- package/gsd-core/templates/state.md +7 -0
- package/gsd-core/templates/verification-report.md +5 -0
- package/gsd-core/workflows/_runtime-launcher.snippet.sh +1 -1
- package/gsd-core/workflows/add-backlog.md +3 -1
- package/gsd-core/workflows/add-phase.md +5 -3
- package/gsd-core/workflows/add-tests.md +4 -9
- package/gsd-core/workflows/add-todo.md +2 -2
- package/gsd-core/workflows/ai-integration-phase.md +5 -10
- package/gsd-core/workflows/analyze-dependencies.md +2 -0
- package/gsd-core/workflows/audit-fix.md +14 -3
- package/gsd-core/workflows/audit-milestone.md +11 -9
- package/gsd-core/workflows/audit-uat.md +19 -2
- package/gsd-core/workflows/autonomous/steps/converge-fail-fast.md +2 -2
- package/gsd-core/workflows/autonomous.md +12 -26
- package/gsd-core/workflows/check-todos.md +2 -2
- package/gsd-core/workflows/cleanup.md +3 -3
- package/gsd-core/workflows/code-review/steps/structural-pre-pass.md +16 -14
- package/gsd-core/workflows/code-review-fix.md +3 -1
- package/gsd-core/workflows/code-review.md +192 -69
- package/gsd-core/workflows/complete-milestone.md +28 -14
- package/gsd-core/workflows/debug.md +6 -4
- package/gsd-core/workflows/diagnose-issues.md +17 -7
- package/gsd-core/workflows/discuss-phase/modes/advisor.md +3 -1
- package/gsd-core/workflows/discuss-phase/modes/all.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/analyze.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/auto.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/batch.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/chain.md +5 -7
- package/gsd-core/workflows/discuss-phase/modes/default.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/power.md +2 -0
- package/gsd-core/workflows/discuss-phase/modes/text.md +3 -1
- package/gsd-core/workflows/discuss-phase/templates/context.md +2 -0
- package/gsd-core/workflows/discuss-phase/templates/discussion-log.md +2 -0
- package/gsd-core/workflows/discuss-phase-assumptions/steps/auto-advance-dispatch.md +1 -3
- package/gsd-core/workflows/discuss-phase-assumptions.md +3 -3
- package/gsd-core/workflows/discuss-phase-power.md +2 -0
- package/gsd-core/workflows/discuss-phase.md +2 -2
- package/gsd-core/workflows/do.md +46 -19
- package/gsd-core/workflows/docs-update.md +6 -5
- package/gsd-core/workflows/edit-phase.md +3 -1
- package/gsd-core/workflows/eval-review.md +5 -10
- package/gsd-core/workflows/execute-phase/steps/codebase-drift-gate.md +3 -1
- package/gsd-core/workflows/execute-phase/steps/executor-isolation-dispatch.md +129 -11
- package/gsd-core/workflows/execute-phase/steps/gap-closure-artifacts.md +1 -1
- package/gsd-core/workflows/execute-phase/steps/partial-wave.md +1 -1
- package/gsd-core/workflows/execute-phase/steps/per-plan-executor-routing.md +1 -1
- package/gsd-core/workflows/execute-phase/steps/per-plan-worktree-gate.md +29 -5
- package/gsd-core/workflows/execute-phase/steps/post-merge-gate.md +2 -2
- package/gsd-core/workflows/execute-phase/steps/protected-branch.md +21 -0
- package/gsd-core/workflows/execute-phase/steps/regression-gate-run.md +4 -2
- package/gsd-core/workflows/execute-phase/steps/tdd-applicability-resolution.md +25 -0
- package/gsd-core/workflows/execute-phase/steps/wave-post-gate-hooks.md +39 -0
- package/gsd-core/workflows/execute-phase/steps/worktree-recovery-policy.md +2 -0
- package/gsd-core/workflows/execute-phase.md +68 -66
- package/gsd-core/workflows/execute-plan.md +25 -20
- package/gsd-core/workflows/explore.md +3 -1
- package/gsd-core/workflows/extract-learnings.md +3 -1
- package/gsd-core/workflows/fast.md +8 -2
- package/gsd-core/workflows/forensics.md +3 -1
- package/gsd-core/workflows/graduation.md +6 -6
- package/gsd-core/workflows/health.md +4 -7
- package/gsd-core/workflows/help/modes/brief.md +2 -0
- package/gsd-core/workflows/help/modes/default.md +2 -0
- package/gsd-core/workflows/help/modes/full.md +12 -0
- package/gsd-core/workflows/help/modes/topic.md +2 -0
- package/gsd-core/workflows/help.md +2 -0
- package/gsd-core/workflows/import.md +17 -14
- package/gsd-core/workflows/inbox.md +5 -6
- package/gsd-core/workflows/ingest-docs.md +45 -12
- package/gsd-core/workflows/insert-phase.md +7 -5
- package/gsd-core/workflows/list-phase-assumptions.md +2 -0
- package/gsd-core/workflows/list-seeds.md +7 -3
- package/gsd-core/workflows/list-workspaces.md +3 -1
- package/gsd-core/workflows/manager.md +15 -26
- package/gsd-core/workflows/map-codebase.md +3 -1
- package/gsd-core/workflows/milestone-summary.md +3 -1
- package/gsd-core/workflows/mvp-phase.md +3 -3
- package/gsd-core/workflows/new-milestone.md +10 -22
- package/gsd-core/workflows/new-project/steps/auto-mode-config.md +1 -1
- package/gsd-core/workflows/new-project.md +17 -29
- package/gsd-core/workflows/new-workspace.md +2 -2
- package/gsd-core/workflows/next.md +4 -2
- package/gsd-core/workflows/node-repair.md +2 -0
- package/gsd-core/workflows/note.md +2 -0
- package/gsd-core/workflows/onboard.md +1 -1
- package/gsd-core/workflows/pause-work.md +20 -5
- package/gsd-core/workflows/plan-phase/steps/adr-ingest-express-path.md +1 -1
- package/gsd-core/workflows/plan-phase/steps/chunked-planning-mode.md +100 -18
- package/gsd-core/workflows/plan-phase/steps/prd-express-path.md +4 -4
- package/gsd-core/workflows/plan-phase/steps/stall-detection-helpers.md +12 -3
- package/gsd-core/workflows/plan-phase.md +251 -54
- package/gsd-core/workflows/plan-review-convergence.md +148 -19
- package/gsd-core/workflows/plant-seed.md +3 -3
- package/gsd-core/workflows/pr-branch.md +195 -51
- package/gsd-core/workflows/profile-user.md +17 -15
- package/gsd-core/workflows/progress/steps/forensic-audit.md +1 -1
- package/gsd-core/workflows/progress.md +52 -15
- package/gsd-core/workflows/quick/steps/discussion-phase.md +1 -3
- package/gsd-core/workflows/quick/steps/plan-checker-loop.md +38 -5
- package/gsd-core/workflows/quick/steps/quick-verification.md +2 -4
- package/gsd-core/workflows/quick/steps/research-phase.md +5 -7
- package/gsd-core/workflows/quick/steps/worktree-pre-dispatch-commit.md +3 -3
- package/gsd-core/workflows/quick-batch/steps/batch-init.md +55 -0
- package/gsd-core/workflows/quick-batch/steps/completion.md +65 -0
- package/gsd-core/workflows/quick-batch/steps/merge-wave.md +100 -0
- package/gsd-core/workflows/quick-batch/steps/plan-checker-loop.md +147 -0
- package/gsd-core/workflows/quick-batch/steps/planner-wave.md +158 -0
- package/gsd-core/workflows/quick-batch/steps/research-phase.md +95 -0
- package/gsd-core/workflows/quick-batch/steps/resume-mode.md +49 -0
- package/gsd-core/workflows/quick-batch/steps/verification-wave.md +73 -0
- package/gsd-core/workflows/quick-batch/steps/worktree-dispatch.md +169 -0
- package/gsd-core/workflows/quick-batch.md +203 -0
- package/gsd-core/workflows/quick.md +33 -32
- package/gsd-core/workflows/reapply-patches.md +2 -0
- package/gsd-core/workflows/remove-phase.md +6 -4
- package/gsd-core/workflows/remove-workspace.md +3 -3
- package/gsd-core/workflows/resume-project.md +14 -14
- package/gsd-core/workflows/review.md +404 -21
- package/gsd-core/workflows/scan.md +3 -1
- package/gsd-core/workflows/section-manifest.json +12 -0
- package/gsd-core/workflows/secure-phase.md +3 -3
- package/gsd-core/workflows/session-report.md +2 -0
- package/gsd-core/workflows/settings-advanced.md +9 -9
- package/gsd-core/workflows/settings-integrations.md +66 -32
- package/gsd-core/workflows/settings.md +4 -6
- package/gsd-core/workflows/ship.md +22 -16
- package/gsd-core/workflows/sketch-wrap-up.md +13 -17
- package/gsd-core/workflows/sketch.md +13 -19
- package/gsd-core/workflows/smart-entry.md +4 -6
- package/gsd-core/workflows/spec-phase.md +31 -4
- package/gsd-core/workflows/spike-wrap-up.md +9 -11
- package/gsd-core/workflows/spike.md +21 -32
- package/gsd-core/workflows/stats.md +4 -2
- package/gsd-core/workflows/sync-skills.md +13 -5
- package/gsd-core/workflows/thread.md +13 -7
- package/gsd-core/workflows/transition.md +7 -5
- package/gsd-core/workflows/ui-phase.md +36 -21
- package/gsd-core/workflows/ui-review.md +7 -11
- package/gsd-core/workflows/ultraplan-phase.md +7 -13
- package/gsd-core/workflows/undo.md +9 -17
- package/gsd-core/workflows/update.md +47 -48
- package/gsd-core/workflows/validate-phase.md +3 -3
- package/gsd-core/workflows/verify-work/steps/automated-ui-verification.md +25 -1
- package/gsd-core/workflows/verify-work/steps/mvp-uat-framing.md +1 -1
- package/gsd-core/workflows/verify-work.md +106 -21
- package/hooks/dist/gsd-agent-isolation-guard.js +77 -38
- package/hooks/dist/gsd-check-update-worker.js +19 -2
- package/hooks/dist/gsd-config-reload.js +18 -12
- package/hooks/dist/gsd-context-monitor.js +302 -22
- package/hooks/dist/gsd-cursor-post-tool.js +3 -1
- package/hooks/dist/gsd-cursor-pre-tool.js +3 -1
- package/hooks/dist/gsd-cursor-session-start.js +2 -1
- package/hooks/dist/gsd-cursor-stop.js +2 -1
- package/hooks/dist/gsd-cursor-subagent-start.js +28 -23
- package/hooks/dist/gsd-cursor-subagent-stop.js +3 -1
- package/hooks/dist/gsd-ensure-canonical-path.js +2 -1
- package/hooks/dist/gsd-graphify-update.sh +22 -18
- package/hooks/dist/gsd-node-runner.sh +77 -0
- package/hooks/dist/gsd-phase-boundary.sh +1 -0
- package/hooks/dist/gsd-prompt-guard.js +46 -12
- package/hooks/dist/gsd-read-guard.js +18 -7
- package/hooks/dist/gsd-read-injection-scanner.js +22 -13
- package/hooks/dist/gsd-secret-read-guard.js +1079 -0
- package/hooks/dist/gsd-session-state.sh +1 -0
- package/hooks/dist/gsd-statusline.js +222 -29
- package/hooks/dist/gsd-validate-commit.sh +523 -12
- package/hooks/dist/gsd-windsurf-pre-command.js +16 -11
- package/hooks/dist/gsd-windsurf-pre-write.js +22 -13
- package/hooks/dist/gsd-workflow-guard.js +36 -17
- package/hooks/dist/gsd-worktree-path-guard.js +36 -21
- package/hooks/dist/gsd-write-guard.js +35 -25
- package/hooks/dist/lib/cli-exit.js +560 -0
- package/hooks/dist/lib/exit-code-registry.js +98 -0
- package/hooks/dist/lib/git-cmd.js +210 -1
- package/hooks/dist/lib/git-probe.js +84 -0
- package/hooks/dist/lib/hook-exit.js +81 -0
- package/hooks/dist/lib/injection-patterns.js +36 -6
- package/hooks/dist/managed-hooks-registry.cjs +4 -0
- package/hooks/gsd-agent-isolation-guard.js +77 -38
- package/hooks/gsd-check-update-worker.js +19 -2
- package/hooks/gsd-config-reload.js +18 -12
- package/hooks/gsd-context-monitor.js +302 -22
- package/hooks/gsd-cursor-post-tool.js +3 -1
- package/hooks/gsd-cursor-pre-tool.js +3 -1
- package/hooks/gsd-cursor-session-start.js +2 -1
- package/hooks/gsd-cursor-stop.js +2 -1
- package/hooks/gsd-cursor-subagent-start.js +28 -23
- package/hooks/gsd-cursor-subagent-stop.js +3 -1
- package/hooks/gsd-ensure-canonical-path.js +2 -1
- package/hooks/gsd-graphify-update.sh +22 -18
- package/hooks/gsd-node-runner.sh +77 -0
- package/hooks/gsd-phase-boundary.sh +1 -0
- package/hooks/gsd-prompt-guard.js +46 -12
- package/hooks/gsd-read-guard.js +18 -7
- package/hooks/gsd-read-injection-scanner.js +22 -13
- package/hooks/gsd-secret-read-guard.js +1079 -0
- package/hooks/gsd-session-state.sh +1 -0
- package/hooks/gsd-statusline.js +222 -29
- package/hooks/gsd-validate-commit.sh +523 -12
- package/hooks/gsd-windsurf-pre-command.js +16 -11
- package/hooks/gsd-windsurf-pre-write.js +22 -13
- package/hooks/gsd-workflow-guard.js +36 -17
- package/hooks/gsd-worktree-path-guard.js +36 -21
- package/hooks/gsd-write-guard.js +35 -25
- package/hooks/hooks.json +6 -0
- package/hooks/lib/cli-exit.js +560 -0
- package/hooks/lib/exit-code-registry.js +98 -0
- package/hooks/lib/git-cmd.js +210 -1
- package/hooks/lib/git-probe.js +84 -0
- package/hooks/lib/hook-exit.js +81 -0
- package/hooks/lib/injection-patterns.js +36 -6
- package/hooks/managed-hooks-registry.cjs +4 -0
- package/package.json +14 -9
- package/scripts/base64-scan.sh +74 -12
- package/scripts/build-hooks.js +12 -0
- package/scripts/check-glossary-refs.cjs +77 -15
- package/scripts/check-mutation-score-ratchet.cjs +156 -0
- package/scripts/ci-check-job-near-cap.cjs +49 -0
- package/scripts/ci-pr-mergeability.cjs +262 -0
- package/scripts/ci-test-scope.cjs +52 -12
- package/scripts/ci-timeout-report.cjs +230 -0
- package/scripts/docs-guard-registry.cjs +406 -0
- package/scripts/gen-capability-registry.cjs +8 -6
- package/scripts/gen-exit-code-docs.cjs +318 -0
- package/scripts/gen-exit-code-registry.cjs +891 -0
- package/scripts/gen-features.cjs +836 -0
- package/scripts/gen-hooks-cli-exit.cjs +239 -0
- package/scripts/gen-install-tree-fixtures.cjs +2 -2
- package/scripts/gen-loop-host-contract.cjs +189 -4
- package/scripts/gen-scripts-cli-exit.cjs +185 -0
- package/scripts/gen-state-md-docs.cjs +727 -0
- package/scripts/{test-failure-reasons.cjs → gsd-test-gate-reasons.cjs} +6 -0
- package/scripts/lib/ci-job-timing.cjs +72 -0
- package/scripts/lib/cli-exit.cjs +546 -44
- package/scripts/lib/drift-scan.cjs +32 -2
- package/scripts/lib/exit-code-registry.cjs +98 -0
- package/scripts/lib/ndjson-reporter.cjs +119 -0
- package/scripts/lib/shellcheck-fetch.cjs +247 -0
- package/scripts/lint-allow-test-rule-refs.allowlist.json +0 -6
- package/scripts/lint-allow-test-rule-refs.effective-ceiling.json +1 -1
- package/scripts/lint-allow-test-rule-refs.unverified-ceiling.json +1 -1
- package/scripts/lint-docs-guard-registration.cjs +495 -0
- package/scripts/lint-docs-guard-registration.exempt-baseline.cjs +198 -0
- package/scripts/lint-eslint-glob-coverage.allowlist.json +4 -0
- package/scripts/{lint-fix-has-regression-test.cjs → lint-fix-has-regression-tests.cjs} +12 -6
- package/scripts/lint-health-diagnostic-rule-table.cjs +65 -8
- package/scripts/lint-mutation-test-derivation-drift.cjs +86 -0
- package/scripts/lint-phase-enumeration-drift.cjs +45 -14
- package/scripts/lint-phase-id-drift.cjs +133 -8
- package/scripts/lint-planning-prompt-drift.cjs +38 -1
- package/scripts/lint-portable-grep.cjs +176 -0
- package/scripts/lint-removed-but-needed.cjs +184 -16
- package/scripts/lint-response-language-coverage.cjs +524 -0
- package/scripts/lint-seam-enforcement.cjs +182 -0
- package/scripts/lint-slug-derivation-drift.cjs +921 -0
- package/scripts/lint-source-test-name-collision.cjs +241 -0
- package/scripts/lint-state-write-path-drift.cjs +337 -432
- package/scripts/lint-test-file-count.allowlist.json +124 -4
- package/scripts/lint-test-file-count.cjs +25 -3
- package/scripts/lint-unreachable-guard-drift.cjs +51 -64
- package/scripts/lint-vendored-deps.cjs +208 -35
- package/scripts/lint-workflow-shellcheck-baseline.json +1027 -0
- package/scripts/lint-workflow-shellcheck.cjs +614 -0
- package/scripts/mutation-matrix.cjs +599 -50
- package/scripts/npm-audit-baseline.cjs +376 -0
- package/scripts/prompt-injection-scan.sh +83 -14
- package/scripts/require-issue-link-policy.cjs +16 -1
- package/scripts/secret-scan.sh +75 -13
- package/scripts/select-docs-guards.cjs +56 -0
- package/scripts/sync-runtime-launcher.cjs +22 -3
- package/skills/gsd-discuss-phase/SKILL.md +1 -1
- package/skills/gsd-execute-phase/SKILL.md +1 -1
- package/skills/gsd-import/SKILL.md +1 -1
- package/skills/gsd-ns-workflow/SKILL.md +1 -0
- package/skills/gsd-phase/SKILL.md +1 -1
- package/skills/gsd-quick/SKILL.md +8 -4
- package/skills/gsd-quick-batch/SKILL.md +105 -0
- package/skills/gsd-surface/SKILL.md +18 -8
- package/vscode/package.json +1 -1
- package/bin/lib/ui-safety-gate.cjs +0 -109
- package/scripts/lint-emitted-drift-ack.cjs +0 -344
- package/scripts/state-write-path-drift-baseline.json +0 -19
|
@@ -0,0 +1,318 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
'use strict';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* gen-exit-code-docs.cjs — ADR-3889 (#3913), the terminal phase of the exit-
|
|
6
|
+
* code-registry epic.
|
|
7
|
+
*
|
|
8
|
+
* Generates docs/reference/exit-codes.md FROM the exit-code declaration
|
|
9
|
+
* (gsd-core/bin/shared/exit-codes.json), so the human-facing reference page
|
|
10
|
+
* can never drift from the actual registered codes — the same allocator-less
|
|
11
|
+
* failure mode this epic exists to close, now closed for the doc surface too.
|
|
12
|
+
* Modelled directly on scripts/gen-capability-matrix.cjs ->
|
|
13
|
+
* docs/reference/capability-matrix.md: same --check/--write/stdout modes,
|
|
14
|
+
* same "generated, do not edit" banner convention, same normalize-then-
|
|
15
|
+
* byte-compare drift check.
|
|
16
|
+
*
|
|
17
|
+
* The declaration JSON is read directly (not the compiled
|
|
18
|
+
* gsd-core/bin/lib/exit-code-registry.cjs artifact, which is gitignored tsc
|
|
19
|
+
* output) so this generator — like scripts/gen-exit-code-registry.cjs itself —
|
|
20
|
+
* works on an unbuilt clone. The "Reserved bands" table below is DERIVED,
|
|
21
|
+
* not retyped: its ranges and allocatable/reserved status come from
|
|
22
|
+
* `classifyBand`/`computeBandRanges`, which are themselves composed
|
|
23
|
+
* entirely from `isAllocatableCode`/`bandFor` in
|
|
24
|
+
* scripts/gen-exit-code-registry.cjs (all four imported below). Only the
|
|
25
|
+
* per-band RATIONALE prose (BAND_PROSE) is hand-authored; widening or
|
|
26
|
+
* narrowing a band in gen-exit-code-registry.cjs changes the ranges this
|
|
27
|
+
* page renders, with no second literal to keep in sync.
|
|
28
|
+
*
|
|
29
|
+
* Usage:
|
|
30
|
+
* node scripts/gen-exit-code-docs.cjs # print to stdout
|
|
31
|
+
* node scripts/gen-exit-code-docs.cjs --write # write the committed file
|
|
32
|
+
* node scripts/gen-exit-code-docs.cjs --check # exit 1 if the committed file is stale
|
|
33
|
+
* node scripts/gen-exit-code-docs.cjs --declaration <path> --out <path> # override for tests
|
|
34
|
+
*/
|
|
35
|
+
|
|
36
|
+
const fs = require('fs');
|
|
37
|
+
const path = require('path');
|
|
38
|
+
const { ExitError, runMain } = require('./lib/cli-exit.cjs');
|
|
39
|
+
const {
|
|
40
|
+
DEFAULT_DECLARATION_PATH,
|
|
41
|
+
loadDeclaration,
|
|
42
|
+
validateEntries,
|
|
43
|
+
computeBandRanges,
|
|
44
|
+
BANDS,
|
|
45
|
+
} = require('./gen-exit-code-registry.cjs');
|
|
46
|
+
|
|
47
|
+
const ROOT = path.resolve(__dirname, '..');
|
|
48
|
+
const DOC_PATH = path.join(ROOT, 'docs', 'reference', 'exit-codes.md');
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* How far above the highest defined band (125, the top of 'domain') to scan
|
|
52
|
+
* when deriving band ranges. Large enough to prove the 'shell-signal'
|
|
53
|
+
* (126+) run is genuinely open-ended (classifyBand is constant well past
|
|
54
|
+
* it), not just an artifact of stopping the scan too early.
|
|
55
|
+
*/
|
|
56
|
+
const BAND_SCAN_MAX = 500;
|
|
57
|
+
|
|
58
|
+
/** Hand-authored rationale prose per band category — the only part of the
|
|
59
|
+
* "Reserved bands" table that stays authored; the ranges themselves are
|
|
60
|
+
* derived by computeBandRanges from isAllocatableCode/bandFor. */
|
|
61
|
+
const BAND_PROSE = Object.freeze({
|
|
62
|
+
free: '**Free — never allocatable.** `0` is the universal "succeeded" convention and `1` is the universal "failed, no further detail" convention across nearly every CLI ecosystem. Registering either here would collide with that universal meaning instead of adding a distinct, named signal — so the registry leaves both permanently unallocated.',
|
|
63
|
+
'hook-only': 'Reserved exclusively to the Claude Code hook-protocol deny (`HOOK_DENY`) — owned by `hook-adapter` and no other module.',
|
|
64
|
+
'node-reserved': '**Node-reserved.** Node.js itself assigns meaning to this range (e.g. internal JavaScript errors, fatal exceptions, invalid argument errors) before a GSD process ever gets a chance to project its own outcome. Allocating one of these would be indistinguishable from a Node-level failure the process never intended to report.',
|
|
65
|
+
'outside-every-band': 'Outside every allocatable band — not Node-reserved, but also not opened for GSD use. `126`+ additionally collides with the shell convention for "command not executable" / "signal N" (`128+N`), which a process exit code must never impersonate.',
|
|
66
|
+
generic: '**Generic band.** Codes any module may use for caller-facing, non-domain-specific outcomes (bad argv, no input in scope, a missing prerequisite, an internal crash).',
|
|
67
|
+
domain: '**Domain band.** Codes reserved for a specific product surface\'s own vocabulary — currently only `gsd-tools`\' `DEGRADED` (a completed run reporting a condition through its payload rather than as a process failure).',
|
|
68
|
+
});
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* The 'shell-signal' category (126+) is folded into the SAME rendered row
|
|
72
|
+
* as 'outside-every-band' (both read "not opened for GSD use" to a reader —
|
|
73
|
+
* the original hand-authored table merged them into one row, and the prose
|
|
74
|
+
* above documents the 126+ collision inline). Every other category gets its
|
|
75
|
+
* own row, in this fixed display order.
|
|
76
|
+
*/
|
|
77
|
+
const CATEGORY_ROW_ORDER = ['free', 'hook-only', 'node-reserved', 'outside-every-band', 'generic', 'domain'];
|
|
78
|
+
const CATEGORY_MERGE_INTO = Object.freeze({ 'shell-signal': 'outside-every-band' });
|
|
79
|
+
|
|
80
|
+
/**
|
|
81
|
+
* Guard against category-set drift across the three authored lists the
|
|
82
|
+
* "Reserved bands" table depends on: BANDS (gen-exit-code-registry.cjs — the
|
|
83
|
+
* single source of every category classifyBand can ever return),
|
|
84
|
+
* CATEGORY_ROW_ORDER (the rendered row order here), and BAND_PROSE (the
|
|
85
|
+
* hand-authored rationale text per row). Nothing type-checks that these three
|
|
86
|
+
* agree, so adding a BANDS category with no row/prose entry silently drops it
|
|
87
|
+
* from the table, and a row with no prose entry renders the literal string
|
|
88
|
+
* "undefined" — see #3913 P9 review finding (unchecked `BAND_PROSE[category]`
|
|
89
|
+
* lookup) and its root cause: three authored lists, only one of them derived.
|
|
90
|
+
* Throws loudly the first time any of the three sets diverge instead of
|
|
91
|
+
* silently omitting a row or rendering `undefined`.
|
|
92
|
+
*/
|
|
93
|
+
function assertBandCategoriesConsistent() {
|
|
94
|
+
// Every category classifyBand can ever return: each BANDS entry's own
|
|
95
|
+
// category, plus the synthetic 'outside-every-band' residual classifyBand
|
|
96
|
+
// falls back to for a code no BANDS entry claims (14-63, 79).
|
|
97
|
+
const producedCategories = new Set([...BANDS.map((b) => b.category), 'outside-every-band']);
|
|
98
|
+
|
|
99
|
+
// 1. Every produced category must resolve — directly, or via
|
|
100
|
+
// CATEGORY_MERGE_INTO — to a row this page actually renders. Otherwise
|
|
101
|
+
// it is silently dropped from the table (the #3913 P9 finding).
|
|
102
|
+
for (const category of producedCategories) {
|
|
103
|
+
const rowCategory = CATEGORY_MERGE_INTO[category] || category;
|
|
104
|
+
if (!CATEGORY_ROW_ORDER.includes(rowCategory)) {
|
|
105
|
+
throw new ExitError(1, `fail_band_category_unaccounted: BANDS category "${category}" resolves to row ` +
|
|
106
|
+
`"${rowCategory}", which is in neither CATEGORY_ROW_ORDER nor a CATEGORY_MERGE_INTO target — add it to ` +
|
|
107
|
+
'one or the other in scripts/gen-exit-code-docs.cjs.');
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
// 2. Every rendered row must have hand-authored rationale prose — otherwise
|
|
112
|
+
// the table cell literally renders the string "undefined".
|
|
113
|
+
for (const category of CATEGORY_ROW_ORDER) {
|
|
114
|
+
if (!(category in BAND_PROSE)) {
|
|
115
|
+
throw new ExitError(1, `fail_band_prose_missing: CATEGORY_ROW_ORDER category "${category}" has no ` +
|
|
116
|
+
'BAND_PROSE entry — it would render the literal string "undefined" in the generated table.');
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
// 3. Reverse drift: a CATEGORY_ROW_ORDER or BAND_PROSE entry naming a
|
|
121
|
+
// category no BANDS entry (nor the 'outside-every-band' residual)
|
|
122
|
+
// produces is stale prose for a band that no longer exists.
|
|
123
|
+
const resolvedRowCategories = new Set(
|
|
124
|
+
[...producedCategories].map((category) => CATEGORY_MERGE_INTO[category] || category),
|
|
125
|
+
);
|
|
126
|
+
for (const category of CATEGORY_ROW_ORDER) {
|
|
127
|
+
if (!resolvedRowCategories.has(category)) {
|
|
128
|
+
throw new ExitError(1, `fail_band_category_stale: CATEGORY_ROW_ORDER names "${category}", which no BANDS ` +
|
|
129
|
+
'entry (directly, or via CATEGORY_MERGE_INTO) produces — remove it, or fix the drift between BANDS in ' +
|
|
130
|
+
'scripts/gen-exit-code-registry.cjs and CATEGORY_MERGE_INTO here.');
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
for (const category of Object.keys(BAND_PROSE)) {
|
|
134
|
+
if (!CATEGORY_ROW_ORDER.includes(category)) {
|
|
135
|
+
throw new ExitError(1, `fail_band_category_stale: BAND_PROSE has an entry for "${category}", which is not ` +
|
|
136
|
+
'in CATEGORY_ROW_ORDER — remove the stale prose, or add the row.');
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
/** Format one contiguous range as a Markdown-table-cell token. */
|
|
142
|
+
function formatRange(range) {
|
|
143
|
+
if (range.openEnded) return `\`${range.start}+\``;
|
|
144
|
+
if (range.start === range.end) return `\`${range.start}\``;
|
|
145
|
+
return `\`${range.start}\`–\`${range.end}\``;
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
/**
|
|
149
|
+
* Render the "Reserved bands" table. Ranges come from computeBandRanges
|
|
150
|
+
* (itself derived from isAllocatableCode/bandFor); only BAND_PROSE and the
|
|
151
|
+
* row grouping/order above are authored.
|
|
152
|
+
*/
|
|
153
|
+
function renderBandTable() {
|
|
154
|
+
assertBandCategoriesConsistent();
|
|
155
|
+
|
|
156
|
+
const byCategory = new Map();
|
|
157
|
+
for (const { category, ranges } of computeBandRanges(BAND_SCAN_MAX)) {
|
|
158
|
+
const rowCategory = CATEGORY_MERGE_INTO[category] || category;
|
|
159
|
+
if (!byCategory.has(rowCategory)) byCategory.set(rowCategory, []);
|
|
160
|
+
byCategory.get(rowCategory).push(...ranges);
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
const rows = CATEGORY_ROW_ORDER.map((category) => {
|
|
164
|
+
const ranges = byCategory.get(category) || [];
|
|
165
|
+
const label = ranges.map(formatRange).join(', ');
|
|
166
|
+
return `| ${label} | ${BAND_PROSE[category]} |`;
|
|
167
|
+
});
|
|
168
|
+
|
|
169
|
+
return ['| Band | Meaning |', '|---|---|', ...rows].join('\n');
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
/** Load + validate the declaration, throwing (loud) on anything malformed — mirrors gen-exit-code-registry.cjs's own gate. */
|
|
173
|
+
function loadEntries(declarationPath) {
|
|
174
|
+
const loaded = loadDeclaration(declarationPath);
|
|
175
|
+
if (!loaded.ok) {
|
|
176
|
+
throw new ExitError(1, `${loaded.reason}: ${loaded.message}`);
|
|
177
|
+
}
|
|
178
|
+
const validated = validateEntries(loaded.entries);
|
|
179
|
+
if (!validated.ok) {
|
|
180
|
+
throw new ExitError(1, `${validated.reason}: ${validated.message}`);
|
|
181
|
+
}
|
|
182
|
+
return loaded.entries;
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
function renderRegisteredTable(entries) {
|
|
186
|
+
const rows = [...entries]
|
|
187
|
+
.sort((a, b) => a.code - b.code)
|
|
188
|
+
.map((e) => `| ${e.code} | \`${e.name}\` | ${e.meaning} | \`${e.owner}\` | ${e.authorizedBy} |`);
|
|
189
|
+
return [
|
|
190
|
+
'| code | name | meaning | owning module | authorized by |',
|
|
191
|
+
'|---|---|---|---|---|',
|
|
192
|
+
...rows,
|
|
193
|
+
].join('\n');
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
function buildDoc(entries) {
|
|
197
|
+
const registeredTable = renderRegisteredTable(entries);
|
|
198
|
+
const registeredCount = entries.length;
|
|
199
|
+
const bandTable = renderBandTable();
|
|
200
|
+
|
|
201
|
+
return `# Exit code reference
|
|
202
|
+
|
|
203
|
+
> **Generated file — do not edit by hand.**
|
|
204
|
+
> This page is generated from the exit-code declaration
|
|
205
|
+
> (\`gsd-core/bin/shared/exit-codes.json\`) by \`scripts/gen-exit-code-docs.cjs\`
|
|
206
|
+
> and kept honest by a drift guard in \`npm run lint:generated-sync\` (which runs
|
|
207
|
+
> \`node scripts/gen-exit-code-docs.cjs --check\`). Any manual edit is overwritten
|
|
208
|
+
> on the next generation run. To register a new code, add an entry to the
|
|
209
|
+
> declaration and run \`node scripts/gen-exit-code-registry.cjs --write && node
|
|
210
|
+
> scripts/gen-exit-code-docs.cjs --write\`.
|
|
211
|
+
|
|
212
|
+
See also: [ADR-3889 — one exit-code registry](../adr/3889-process-exit-contract.md) —
|
|
213
|
+
[Adopt the v2 exit contract](../how-to/adopt-the-v2-exit-contract.md) —
|
|
214
|
+
[JSON error mode](../json-errors.md)
|
|
215
|
+
|
|
216
|
+
---
|
|
217
|
+
|
|
218
|
+
## Registered codes (${registeredCount})
|
|
219
|
+
|
|
220
|
+
Every process-level exit code \`gsd-tools\`, its hooks, and its scripts may terminate
|
|
221
|
+
with, by name, meaning, and the module that owns it.
|
|
222
|
+
|
|
223
|
+
${registeredTable}
|
|
224
|
+
|
|
225
|
+
---
|
|
226
|
+
|
|
227
|
+
## Reserved bands
|
|
228
|
+
|
|
229
|
+
The registered codes above are not chosen freely — each falls inside one of a
|
|
230
|
+
fixed set of allocatable bands (ADR-3889 §1). A code outside these bands can
|
|
231
|
+
never be registered; validation rejects it before it reaches the tables above.
|
|
232
|
+
This is what makes an unfamiliar number in a CI log actionable: look up its
|
|
233
|
+
band first, then its registered name if it has one.
|
|
234
|
+
|
|
235
|
+
${bandTable}
|
|
236
|
+
|
|
237
|
+
## The v1/v2 exit contract
|
|
238
|
+
|
|
239
|
+
ADR-3889 §4 adds a **version projection** on top of this registry, not a second
|
|
240
|
+
registry: every registered name above projects to the *same* code under both
|
|
241
|
+
contract versions, with one deliberate exception — \`DEGRADED\`. Under the
|
|
242
|
+
default, backward-compatible \`v1\` contract, a payload-carried error
|
|
243
|
+
(\`output({error})\`) still exits \`0\`, exactly as
|
|
244
|
+
[ADR-2980](../adr/2980-payload-carried-error-is-a-degraded-result.md) ratified
|
|
245
|
+
for the pre-existing call sites that already depended on that behavior — **64**
|
|
246
|
+
call sites across 9 modules per that ADR's own amendment (its original text
|
|
247
|
+
said ~60). Under the
|
|
248
|
+
opt-in \`v2\` contract, the same outcome exits \`80\` (\`DEGRADED\`) instead, so a
|
|
249
|
+
caller that wants to branch on the exit code alone — without parsing stdout —
|
|
250
|
+
can opt in without breaking every existing consumer. See
|
|
251
|
+
[Adopt the v2 exit contract](../how-to/adopt-the-v2-exit-contract.md) for how to
|
|
252
|
+
turn this on, and [JSON error mode](../json-errors.md) for the full fault vs.
|
|
253
|
+
degraded-result channel taxonomy this registry sits underneath.
|
|
254
|
+
`;
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
/** Normalize CRLF→LF + ensure a single trailing newline, for cross-platform compare. */
|
|
258
|
+
function normalize(s) {
|
|
259
|
+
return s.replace(/\r\n/g, '\n').replace(/\n+$/, '\n');
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
/**
|
|
263
|
+
* Parse the small flag set this CLI accepts. `--declaration`/`--out` exist
|
|
264
|
+
* only so tests can redirect both the source and the target to a tmpdir
|
|
265
|
+
* without ever touching the real committed declaration or doc page — the
|
|
266
|
+
* same reason scripts/gen-exit-code-registry.cjs and
|
|
267
|
+
* scripts/gen-capability-matrix.cjs's sibling generators take path overrides.
|
|
268
|
+
*/
|
|
269
|
+
function parseArgs(argv) {
|
|
270
|
+
let mode = null;
|
|
271
|
+
let declarationPath = null;
|
|
272
|
+
let outPath = null;
|
|
273
|
+
for (let i = 0; i < argv.length; i++) {
|
|
274
|
+
const arg = argv[i];
|
|
275
|
+
if (arg === '--check' || arg === '--write') {
|
|
276
|
+
mode = arg.slice(2);
|
|
277
|
+
} else if (arg === '--declaration') {
|
|
278
|
+
declarationPath = argv[++i];
|
|
279
|
+
} else if (arg === '--out') {
|
|
280
|
+
outPath = argv[++i];
|
|
281
|
+
} else {
|
|
282
|
+
throw new ExitError(1, `unrecognized argument: ${arg}`);
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
return { mode, declarationPath, outPath };
|
|
286
|
+
}
|
|
287
|
+
|
|
288
|
+
function main() {
|
|
289
|
+
const { mode, declarationPath, outPath } = parseArgs(process.argv.slice(2));
|
|
290
|
+
const docPath = outPath || DOC_PATH;
|
|
291
|
+
const entries = loadEntries(declarationPath || DEFAULT_DECLARATION_PATH);
|
|
292
|
+
const content = buildDoc(entries);
|
|
293
|
+
|
|
294
|
+
if (mode === 'check') {
|
|
295
|
+
let committed;
|
|
296
|
+
try {
|
|
297
|
+
committed = fs.readFileSync(docPath, 'utf8');
|
|
298
|
+
} catch {
|
|
299
|
+
throw new ExitError(1, `${path.relative(ROOT, docPath)} is missing. Run:\n node scripts/gen-exit-code-docs.cjs --write`);
|
|
300
|
+
}
|
|
301
|
+
if (normalize(committed) !== normalize(content)) {
|
|
302
|
+
throw new ExitError(1, `${path.relative(ROOT, docPath)} is stale. Run:\n node scripts/gen-exit-code-docs.cjs --write`);
|
|
303
|
+
}
|
|
304
|
+
console.log(`${path.relative(ROOT, docPath)} is up to date.`);
|
|
305
|
+
return;
|
|
306
|
+
}
|
|
307
|
+
if (mode === 'write') {
|
|
308
|
+
fs.mkdirSync(path.dirname(docPath), { recursive: true });
|
|
309
|
+
fs.writeFileSync(docPath, content, 'utf8');
|
|
310
|
+
console.log(`Wrote ${path.relative(ROOT, docPath)}`);
|
|
311
|
+
return;
|
|
312
|
+
}
|
|
313
|
+
process.stdout.write(content);
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
if (require.main === module) runMain(main);
|
|
317
|
+
|
|
318
|
+
module.exports = { buildDoc, loadEntries, DOC_PATH };
|