@opengsd/gsd-core 1.15.0 → 1.17.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.
Files changed (505) hide show
  1. package/.claude-plugin/marketplace.json +1 -1
  2. package/.claude-plugin/plugin.json +1 -2
  3. package/.opencode/plugins/gsd-core.js +336 -6
  4. package/.opencode/plugins/gsd-statusline/tui.tsx +55 -0
  5. package/GEMINI.md +1 -1
  6. package/agents/gsd-code-fixer.compact.md +1 -1
  7. package/agents/gsd-code-fixer.md +1 -1
  8. package/agents/gsd-code-reviewer.compact.md +5 -3
  9. package/agents/gsd-code-reviewer.md +8 -6
  10. package/agents/gsd-debug-session-manager.compact.md +7 -1
  11. package/agents/gsd-debug-session-manager.md +7 -1
  12. package/agents/gsd-debugger.md +2 -2
  13. package/agents/gsd-eval-auditor.compact.md +1 -1
  14. package/agents/gsd-eval-auditor.md +1 -1
  15. package/agents/gsd-executor.md +4 -4
  16. package/agents/gsd-intel-updater.compact.md +1 -1
  17. package/agents/gsd-intel-updater.md +1 -1
  18. package/agents/gsd-mempalace-curator.md +2 -2
  19. package/agents/gsd-phase-researcher.md +1 -1
  20. package/agents/gsd-plan-checker.md +7 -2
  21. package/agents/gsd-planner.md +3 -3
  22. package/agents/gsd-project-researcher.compact.md +1 -1
  23. package/agents/gsd-project-researcher.md +1 -1
  24. package/agents/gsd-research-synthesizer.compact.md +1 -1
  25. package/agents/gsd-research-synthesizer.md +1 -1
  26. package/agents/gsd-ui-auditor.compact.md +21 -30
  27. package/agents/gsd-ui-auditor.md +42 -51
  28. package/agents/gsd-ui-researcher.compact.md +1 -1
  29. package/agents/gsd-ui-researcher.md +1 -1
  30. package/agents/gsd-verifier.md +31 -9
  31. package/bin/gsd-mcp-server.js +3 -1
  32. package/bin/install.js +487 -290
  33. package/commands/gsd/add-tests.md +6 -1
  34. package/commands/gsd/ai-integration-phase.md +6 -1
  35. package/commands/gsd/audit-fix.md +5 -0
  36. package/commands/gsd/audit-milestone.md +6 -1
  37. package/commands/gsd/autonomous.md +5 -0
  38. package/commands/gsd/capture.md +8 -4
  39. package/commands/gsd/code-review.md +7 -2
  40. package/commands/gsd/complete-milestone.md +4 -0
  41. package/commands/gsd/config.md +7 -3
  42. package/commands/gsd/debug.md +11 -7
  43. package/commands/gsd/discuss-phase.md +7 -3
  44. package/commands/gsd/docs-update.md +12 -7
  45. package/commands/gsd/eval-review.md +6 -1
  46. package/commands/gsd/execute-phase.md +12 -7
  47. package/commands/gsd/extract-learnings.md +5 -0
  48. package/commands/gsd/fast.md +4 -0
  49. package/commands/gsd/forensics.md +5 -1
  50. package/commands/gsd/graphify.md +10 -6
  51. package/commands/gsd/health.md +5 -0
  52. package/commands/gsd/help.md +7 -2
  53. package/commands/gsd/import.md +7 -3
  54. package/commands/gsd/inbox.md +5 -0
  55. package/commands/gsd/ingest-docs.md +5 -1
  56. package/commands/gsd/manager.md +6 -1
  57. package/commands/gsd/map-codebase.md +7 -3
  58. package/commands/gsd/mempalace-capture.md +5 -1
  59. package/commands/gsd/mempalace-recall.md +5 -1
  60. package/commands/gsd/milestone-summary.md +5 -1
  61. package/commands/gsd/mvp-phase.md +8 -3
  62. package/commands/gsd/new-milestone.md +6 -1
  63. package/commands/gsd/new-project.md +5 -0
  64. package/commands/gsd/next.md +6 -1
  65. package/commands/gsd/ns-context.md +4 -0
  66. package/commands/gsd/ns-ideate.md +4 -0
  67. package/commands/gsd/ns-manage.md +4 -0
  68. package/commands/gsd/ns-project.md +4 -0
  69. package/commands/gsd/ns-review.md +4 -0
  70. package/commands/gsd/ns-workflow.md +4 -0
  71. package/commands/gsd/onboard.md +6 -1
  72. package/commands/gsd/pause-work.md +5 -1
  73. package/commands/gsd/phase.md +8 -4
  74. package/commands/gsd/plan-phase.md +6 -1
  75. package/commands/gsd/plan-review-convergence.md +5 -1
  76. package/commands/gsd/pr-branch.md +4 -0
  77. package/commands/gsd/profile-user.md +5 -1
  78. package/commands/gsd/progress.md +6 -1
  79. package/commands/gsd/quick-batch.md +20 -8
  80. package/commands/gsd/quick.md +12 -7
  81. package/commands/gsd/review.md +5 -1
  82. package/commands/gsd/secure-phase.md +6 -1
  83. package/commands/gsd/ship.md +5 -0
  84. package/commands/gsd/sketch.md +7 -2
  85. package/commands/gsd/spec-phase.md +5 -1
  86. package/commands/gsd/spike.md +8 -3
  87. package/commands/gsd/surface.md +5 -1
  88. package/commands/gsd/thread.md +4 -0
  89. package/commands/gsd/ui-phase.md +6 -1
  90. package/commands/gsd/ui-review.md +6 -1
  91. package/commands/gsd/ultraplan-phase.md +5 -1
  92. package/commands/gsd/undo.md +5 -1
  93. package/commands/gsd/update.md +6 -2
  94. package/commands/gsd/validate-phase.md +6 -1
  95. package/commands/gsd/verify-work.md +6 -1
  96. package/commands/gsd/workspace.md +7 -3
  97. package/gsd-core/bin/gsd-tools.cjs +159 -58
  98. package/gsd-core/bin/lib/active-workstream-store.cjs +15 -0
  99. package/gsd-core/bin/lib/adr-parser.cjs +37 -5
  100. package/gsd-core/bin/lib/agent-install-check.cjs +4 -1
  101. package/gsd-core/bin/lib/audit.cjs +78 -44
  102. package/gsd-core/bin/lib/broken-windows.cjs +13 -13
  103. package/gsd-core/bin/lib/capability-activation.cjs +9 -4
  104. package/gsd-core/bin/lib/capability-registry.cjs +249 -117
  105. package/gsd-core/bin/lib/capability-validator.cjs +18 -1
  106. package/gsd-core/bin/lib/capability-writer.cjs +2 -1
  107. package/gsd-core/bin/lib/check-auto-mode.cjs +35 -0
  108. package/gsd-core/bin/lib/check-command-router.cjs +164 -1712
  109. package/gsd-core/bin/lib/cjs-command-router-adapter.cjs +13 -2
  110. package/gsd-core/bin/lib/cli-exit.cjs +12 -0
  111. package/gsd-core/bin/lib/codex-agent-toml.cjs +11 -8
  112. package/gsd-core/bin/lib/command-aliases.cjs +7 -0
  113. package/gsd-core/bin/lib/command-routing-hub.cjs +48 -1
  114. package/gsd-core/bin/lib/commands.cjs +201 -178
  115. package/gsd-core/bin/lib/complexity-trigger.cjs +8 -7
  116. package/gsd-core/bin/lib/config.cjs +43 -12
  117. package/gsd-core/bin/lib/core-utils.cjs +6 -1
  118. package/gsd-core/bin/lib/coverage.cjs +4 -8
  119. package/gsd-core/bin/lib/decision-coverage-support.cjs +259 -0
  120. package/gsd-core/bin/lib/drift.cjs +177 -42
  121. package/gsd-core/bin/lib/frontmatter-fence.cjs +90 -0
  122. package/gsd-core/bin/lib/frontmatter-splice.cjs +494 -0
  123. package/gsd-core/bin/lib/frontmatter.cjs +413 -234
  124. package/gsd-core/bin/lib/gap-checker.cjs +72 -29
  125. package/gsd-core/bin/lib/gate-api-coverage-verify-pre.cjs +381 -0
  126. package/gsd-core/bin/lib/gate-args.cjs +53 -0
  127. package/gsd-core/bin/lib/gate-codebase-drift.cjs +285 -0
  128. package/gsd-core/bin/lib/gate-config.cjs +46 -0
  129. package/gsd-core/bin/lib/gate-context-drift.cjs +142 -0
  130. package/gsd-core/bin/lib/gate-decision-coverage-plan.cjs +169 -0
  131. package/gsd-core/bin/lib/gate-decision-coverage-verify.cjs +126 -0
  132. package/gsd-core/bin/lib/gate-evaluation-scope.cjs +555 -0
  133. package/gsd-core/bin/lib/gate-evidence.cjs +138 -0
  134. package/gsd-core/bin/lib/gate-exit.cjs +27 -0
  135. package/gsd-core/bin/lib/gate-gap-analysis-plan-post.cjs +61 -0
  136. package/gsd-core/bin/lib/gate-phase-context.cjs +170 -0
  137. package/gsd-core/bin/lib/gate-predicate-evaluator.cjs +1 -1
  138. package/gsd-core/bin/lib/gate-predicate.cjs +165 -0
  139. package/gsd-core/bin/lib/gate-prohibition-enforcement.cjs +94 -0
  140. package/gsd-core/bin/lib/gate-schema-drift.cjs +165 -0
  141. package/gsd-core/bin/lib/gate-tdd-red-evidence.cjs +100 -0
  142. package/gsd-core/bin/lib/gate-tdd-review-checkpoint.cjs +182 -0
  143. package/gsd-core/bin/lib/gate-ui-plan.cjs +86 -0
  144. package/gsd-core/bin/lib/gate-ui-safety.cjs +81 -0
  145. package/gsd-core/bin/lib/gate-verdict.cjs +64 -0
  146. package/gsd-core/bin/lib/gate-verify-command-paths.cjs +78 -0
  147. package/gsd-core/bin/lib/gate-verify-failure-directions.cjs +41 -0
  148. package/gsd-core/bin/lib/graphify.cjs +3 -2
  149. package/gsd-core/bin/lib/health-diagnostic-rules/phase-structure.cjs +43 -47
  150. package/gsd-core/bin/lib/health-diagnostic.cjs +45 -8
  151. package/gsd-core/bin/lib/init.cjs +194 -108
  152. package/gsd-core/bin/lib/install-engine.cjs +30 -35
  153. package/gsd-core/bin/lib/install-profiles.cjs +7 -4
  154. package/gsd-core/bin/lib/install-shadow-report.cjs +12 -0
  155. package/gsd-core/bin/lib/installer-migrations/011-opencode-mcp-no-prompts.cjs +99 -0
  156. package/gsd-core/bin/lib/installer-migrations.cjs +54 -1
  157. package/gsd-core/bin/lib/io.cjs +122 -3
  158. package/gsd-core/bin/lib/jsonc-edit.cjs +418 -0
  159. package/gsd-core/bin/lib/loop-host-contract.cjs +2 -1
  160. package/gsd-core/bin/lib/loop-resolver.cjs +95 -0
  161. package/gsd-core/bin/lib/markdown-sectionizer.cjs +75 -1
  162. package/gsd-core/bin/lib/mcp-server.cjs +5 -1
  163. package/gsd-core/bin/lib/milestone.cjs +19 -1
  164. package/gsd-core/bin/lib/model-resolver.cjs +18 -18
  165. package/gsd-core/bin/lib/observability/event.cjs +1 -1
  166. package/gsd-core/bin/lib/observability/logger.cjs +46 -1
  167. package/gsd-core/bin/lib/opencode-mcp-entry.cjs +39 -0
  168. package/gsd-core/bin/lib/opencode-version.cjs +486 -0
  169. package/gsd-core/bin/lib/pattern.cjs +10 -0
  170. package/gsd-core/bin/lib/phase-command-router.cjs +11 -4
  171. package/gsd-core/bin/lib/phase-estimation.cjs +5 -4
  172. package/gsd-core/bin/lib/phase-id.cjs +1 -1
  173. package/gsd-core/bin/lib/phase-lifecycle.cjs +9 -2
  174. package/gsd-core/bin/lib/phase-status.cjs +360 -0
  175. package/gsd-core/bin/lib/phase.cjs +301 -80
  176. package/gsd-core/bin/lib/plan-document.cjs +93 -19
  177. package/gsd-core/bin/lib/plan-drift-guard.cjs +5 -0
  178. package/gsd-core/bin/lib/planning-document.cjs +273 -40
  179. package/gsd-core/bin/lib/planning-inspect.cjs +42 -8
  180. package/gsd-core/bin/lib/planning-snapshot.cjs +18 -0
  181. package/gsd-core/bin/lib/planning-workspace.cjs +76 -53
  182. package/gsd-core/bin/lib/pristine-baseline.cjs +10 -0
  183. package/gsd-core/bin/lib/profile-output.cjs +6 -3
  184. package/gsd-core/bin/lib/prohibition-enforcement.cjs +0 -55
  185. package/gsd-core/bin/lib/quick-batch-command-router.cjs +35 -9
  186. package/gsd-core/bin/lib/quick-batch-dispatch.cjs +13 -9
  187. package/gsd-core/bin/lib/real-home-guard.cjs +9 -1
  188. package/gsd-core/bin/lib/report-parser.cjs +269 -0
  189. package/gsd-core/bin/lib/roadmap-command-router.cjs +13 -15
  190. package/gsd-core/bin/lib/roadmap-parser.cjs +82 -15
  191. package/gsd-core/bin/lib/roadmap-upgrade.cjs +127 -65
  192. package/gsd-core/bin/lib/roadmap.cjs +169 -72
  193. package/gsd-core/bin/lib/runtime-artifact-conversion.cjs +186 -161
  194. package/gsd-core/bin/lib/runtime-artifact-install-plan.cjs +2 -1
  195. package/gsd-core/bin/lib/runtime-artifact-layout.cjs +57 -1
  196. package/gsd-core/bin/lib/runtime-homes.cjs +13 -10
  197. package/gsd-core/bin/lib/runtime-hooks-surface.cjs +365 -594
  198. package/gsd-core/bin/lib/runtime-name-policy.cjs +142 -27
  199. package/gsd-core/bin/lib/runtime-slash.cjs +60 -30
  200. package/gsd-core/bin/lib/shell-command-projection.cjs +37 -2
  201. package/gsd-core/bin/lib/smart-entry.cjs +111 -56
  202. package/gsd-core/bin/lib/stale-bake-guard.cjs +32 -48
  203. package/gsd-core/bin/lib/state-contract.cjs +15 -18
  204. package/gsd-core/bin/lib/state-document.cjs +100 -22
  205. package/gsd-core/bin/lib/state-transition.cjs +67 -9
  206. package/gsd-core/bin/lib/state.cjs +668 -171
  207. package/gsd-core/bin/lib/surface.cjs +2 -1
  208. package/gsd-core/bin/lib/tdd-red-evidence.cjs +48 -152
  209. package/gsd-core/bin/lib/uat-predicate.cjs +313 -35
  210. package/gsd-core/bin/lib/uat.cjs +424 -7
  211. package/gsd-core/bin/lib/ui-frontend-evidence.cjs +94 -58
  212. package/gsd-core/bin/lib/update-context.cjs +18 -1
  213. package/gsd-core/bin/lib/vendor/README.md +31 -9
  214. package/gsd-core/bin/lib/vendor/saxes.cjs +1934 -0
  215. package/gsd-core/bin/lib/vendor/saxes.cjs.LICENSE.txt +92 -0
  216. package/gsd-core/bin/lib/vendor/tap-parser.cjs +8927 -0
  217. package/gsd-core/bin/lib/vendor/tap-parser.cjs.LICENSE.txt +152 -0
  218. package/gsd-core/bin/lib/verification-command-router.cjs +2 -1
  219. package/gsd-core/bin/lib/verification.cjs +1265 -324
  220. package/gsd-core/bin/lib/verify-command-router.cjs +18 -7
  221. package/gsd-core/bin/lib/verify.cjs +286 -567
  222. package/gsd-core/bin/lib/workstream-inventory-builder.cjs +14 -6
  223. package/gsd-core/bin/lib/workstream-inventory.cjs +31 -21
  224. package/gsd-core/bin/lib/workstream-name-policy.cjs +31 -1
  225. package/gsd-core/bin/lib/workstream.cjs +11 -2
  226. package/gsd-core/bin/shared/config-defaults.manifest.json +5 -0
  227. package/gsd-core/bin/shared/config-schema.manifest.json +4 -0
  228. package/gsd-core/references/autonomous-smart-discuss.md +2 -1
  229. package/gsd-core/references/autonomous-ui-design-contract.md +3 -3
  230. package/gsd-core/references/execute-mvp-tdd.md +5 -10
  231. package/gsd-core/references/execute-phase-between-wave-reset.md +3 -0
  232. package/gsd-core/references/execute-phase-response-language.md +1 -1
  233. package/gsd-core/references/gsd-run-resolver.md +1 -1
  234. package/gsd-core/references/loop-hook-dispatch.md +7 -1
  235. package/gsd-core/references/offer-next.md +1 -1
  236. package/gsd-core/references/planning-config.md +1 -1
  237. package/gsd-core/references/spidr-splitting.md +1 -1
  238. package/gsd-core/references/tdd.md +10 -4
  239. package/gsd-core/references/verifier-phase-gates.md +5 -2
  240. package/gsd-core/references/verify-mvp-mode.md +2 -2
  241. package/gsd-core/references/workstream-flag.md +33 -3
  242. package/gsd-core/templates/README.md +1 -1
  243. package/gsd-core/templates/UAT.md +17 -1
  244. package/gsd-core/templates/config.json +2 -11
  245. package/gsd-core/templates/verification-report.md +1 -1
  246. package/gsd-core/workflows/_runtime-launcher.snippet.sh +1 -1
  247. package/gsd-core/workflows/add-backlog.md +1 -1
  248. package/gsd-core/workflows/add-phase.md +8 -7
  249. package/gsd-core/workflows/add-tests.md +3 -2
  250. package/gsd-core/workflows/add-todo.md +4 -3
  251. package/gsd-core/workflows/ai-integration-phase.md +3 -2
  252. package/gsd-core/workflows/audit-fix.md +1 -1
  253. package/gsd-core/workflows/audit-milestone.md +4 -3
  254. package/gsd-core/workflows/audit-uat.md +1 -1
  255. package/gsd-core/workflows/autonomous.md +28 -18
  256. package/gsd-core/workflows/check-todos.md +6 -5
  257. package/gsd-core/workflows/cleanup.md +1 -1
  258. package/gsd-core/workflows/code-review/steps/structural-pre-pass.md +20 -13
  259. package/gsd-core/workflows/code-review-fix.md +5 -4
  260. package/gsd-core/workflows/code-review.md +100 -91
  261. package/gsd-core/workflows/complete-milestone/detail/elaboration.md +4 -3
  262. package/gsd-core/workflows/complete-milestone.md +12 -7
  263. package/gsd-core/workflows/debug.md +30 -5
  264. package/gsd-core/workflows/diagnose-issues.md +3 -2
  265. package/gsd-core/workflows/discuss-phase/modes/advisor.md +1 -1
  266. package/gsd-core/workflows/discuss-phase/modes/chain.md +1 -1
  267. package/gsd-core/workflows/discuss-phase-assumptions.md +4 -3
  268. package/gsd-core/workflows/discuss-phase.md +4 -3
  269. package/gsd-core/workflows/do.md +1 -1
  270. package/gsd-core/workflows/docs-update.md +4 -3
  271. package/gsd-core/workflows/edit-phase.md +4 -3
  272. package/gsd-core/workflows/eval-review.md +5 -3
  273. package/gsd-core/workflows/execute-phase/detail/elaboration.md +1 -1
  274. package/gsd-core/workflows/execute-phase/steps/code-review-disposition.md +4 -2
  275. package/gsd-core/workflows/execute-phase/steps/codebase-drift-gate.md +15 -4
  276. package/gsd-core/workflows/execute-phase/steps/completion-reconciliation.md +10 -7
  277. package/gsd-core/workflows/execute-phase/steps/executor-isolation-dispatch.md +2 -2
  278. package/gsd-core/workflows/execute-phase/steps/gap-closure-artifacts.md +3 -1
  279. package/gsd-core/workflows/execute-phase/steps/partial-wave.md +2 -2
  280. package/gsd-core/workflows/execute-phase/steps/per-plan-executor-routing.md +1 -1
  281. package/gsd-core/workflows/execute-phase/steps/per-plan-worktree-gate.md +1 -1
  282. package/gsd-core/workflows/execute-phase/steps/post-merge-gate.md +1 -1
  283. package/gsd-core/workflows/execute-phase/steps/protected-branch.md +1 -1
  284. package/gsd-core/workflows/execute-phase/steps/regression-gate-run.md +1 -1
  285. package/gsd-core/workflows/execute-phase/steps/regression-gate.md +2 -0
  286. package/gsd-core/workflows/execute-phase/steps/tdd-applicability-resolution.md +1 -1
  287. package/gsd-core/workflows/execute-phase/steps/verify-phase-goal.md +187 -0
  288. package/gsd-core/workflows/execute-phase/steps/wave-post-gate-hooks.md +2 -3
  289. package/gsd-core/workflows/execute-phase.md +81 -171
  290. package/gsd-core/workflows/execute-plan.md +13 -19
  291. package/gsd-core/workflows/explore.md +2 -2
  292. package/gsd-core/workflows/extract-learnings.md +3 -2
  293. package/gsd-core/workflows/fast.md +1 -1
  294. package/gsd-core/workflows/forensics.md +1 -1
  295. package/gsd-core/workflows/graduation.md +1 -1
  296. package/gsd-core/workflows/health.md +2 -1
  297. package/gsd-core/workflows/import.md +3 -2
  298. package/gsd-core/workflows/inbox.md +1 -1
  299. package/gsd-core/workflows/ingest-docs.md +1 -1
  300. package/gsd-core/workflows/insert-phase.md +4 -3
  301. package/gsd-core/workflows/list-seeds.md +1 -1
  302. package/gsd-core/workflows/list-workspaces.md +1 -1
  303. package/gsd-core/workflows/manager.md +5 -3
  304. package/gsd-core/workflows/map-codebase.md +4 -3
  305. package/gsd-core/workflows/milestone-summary.md +3 -2
  306. package/gsd-core/workflows/mvp-phase.md +14 -14
  307. package/gsd-core/workflows/new-milestone.md +10 -10
  308. package/gsd-core/workflows/new-project/steps/auto-mode-config.md +1 -1
  309. package/gsd-core/workflows/new-project.md +1 -1
  310. package/gsd-core/workflows/new-workspace.md +1 -1
  311. package/gsd-core/workflows/next.md +1 -1
  312. package/gsd-core/workflows/pause-work.md +2 -2
  313. package/gsd-core/workflows/plan-phase/detail/elaboration.md +1 -1
  314. package/gsd-core/workflows/plan-phase/steps/chunked-planning-mode.md +1 -1
  315. package/gsd-core/workflows/plan-phase/steps/closed-phase-gate.md +1 -1
  316. package/gsd-core/workflows/plan-phase/steps/prd-express-path.md +1 -1
  317. package/gsd-core/workflows/plan-phase/steps/stall-detection-helpers.md +1 -1
  318. package/gsd-core/workflows/plan-phase.md +27 -18
  319. package/gsd-core/workflows/plan-review-convergence.md +1 -1
  320. package/gsd-core/workflows/plant-seed.md +1 -1
  321. package/gsd-core/workflows/pr-branch.md +1 -1
  322. package/gsd-core/workflows/profile-user.md +1 -1
  323. package/gsd-core/workflows/progress.md +19 -49
  324. package/gsd-core/workflows/quick/steps/plan-checker-loop.md +4 -2
  325. package/gsd-core/workflows/quick/steps/quick-verification.md +4 -4
  326. package/gsd-core/workflows/quick/steps/worktree-pre-dispatch-commit.md +30 -11
  327. package/gsd-core/workflows/quick-batch/steps/batch-init.md +1 -1
  328. package/gsd-core/workflows/quick-batch/steps/completion.md +1 -1
  329. package/gsd-core/workflows/quick-batch/steps/merge-wave.md +1 -1
  330. package/gsd-core/workflows/quick-batch/steps/planner-wave.md +1 -1
  331. package/gsd-core/workflows/quick-batch/steps/research-phase.md +1 -1
  332. package/gsd-core/workflows/quick-batch/steps/resume-mode.md +1 -1
  333. package/gsd-core/workflows/quick-batch/steps/verification-wave.md +9 -3
  334. package/gsd-core/workflows/quick-batch/steps/worktree-dispatch.md +1 -1
  335. package/gsd-core/workflows/quick-batch.md +15 -10
  336. package/gsd-core/workflows/quick.md +42 -31
  337. package/gsd-core/workflows/remove-phase.md +3 -2
  338. package/gsd-core/workflows/remove-workspace.md +1 -1
  339. package/gsd-core/workflows/resume-project.md +17 -12
  340. package/gsd-core/workflows/review.md +3 -2
  341. package/gsd-core/workflows/scan.md +3 -2
  342. package/gsd-core/workflows/secure-phase.md +11 -12
  343. package/gsd-core/workflows/settings-advanced.md +1 -1
  344. package/gsd-core/workflows/settings-integrations.md +1 -1
  345. package/gsd-core/workflows/settings.md +1 -1
  346. package/gsd-core/workflows/ship.md +12 -12
  347. package/gsd-core/workflows/sketch-wrap-up.md +1 -1
  348. package/gsd-core/workflows/sketch.md +1 -1
  349. package/gsd-core/workflows/smart-entry.md +1 -1
  350. package/gsd-core/workflows/spec-phase.md +1 -1
  351. package/gsd-core/workflows/spike-wrap-up.md +1 -1
  352. package/gsd-core/workflows/spike.md +1 -1
  353. package/gsd-core/workflows/stats.md +1 -1
  354. package/gsd-core/workflows/sync-skills.md +1 -1
  355. package/gsd-core/workflows/thread.md +2 -2
  356. package/gsd-core/workflows/transition.md +13 -23
  357. package/gsd-core/workflows/ui-phase.md +5 -4
  358. package/gsd-core/workflows/ui-review.md +4 -3
  359. package/gsd-core/workflows/ultraplan-phase.md +3 -2
  360. package/gsd-core/workflows/undo.md +1 -1
  361. package/gsd-core/workflows/validate-phase.md +10 -12
  362. package/gsd-core/workflows/verify-work/detail/elaboration.md +43 -3
  363. package/gsd-core/workflows/verify-work/steps/automated-ui-verification.md +1 -1
  364. package/gsd-core/workflows/verify-work/steps/mvp-uat-framing.md +5 -3
  365. package/gsd-core/workflows/verify-work.md +68 -59
  366. package/hooks/dist/gsd-agent-isolation-guard.js +8 -0
  367. package/hooks/dist/gsd-check-update-worker.js +8 -0
  368. package/hooks/dist/gsd-check-update.js +34 -20
  369. package/hooks/dist/gsd-context-monitor.js +45 -13
  370. package/hooks/dist/gsd-cursor-subagent-start.js +8 -0
  371. package/hooks/dist/gsd-secret-read-guard.js +263 -16
  372. package/hooks/dist/gsd-statusline.js +336 -29
  373. package/hooks/dist/gsd-update-banner.js +8 -0
  374. package/hooks/dist/gsd-windsurf-pre-write.js +11 -2
  375. package/hooks/dist/gsd-workflow-guard.js +5 -4
  376. package/hooks/dist/gsd-worktree-path-guard.js +6 -2
  377. package/hooks/dist/lib/cli-exit.js +12 -0
  378. package/hooks/dist/lib/git-probe.js +17 -1
  379. package/hooks/dist/lib/isolation-sentinel.js +2 -2
  380. package/hooks/gsd-agent-isolation-guard.js +8 -0
  381. package/hooks/gsd-check-update-worker.js +8 -0
  382. package/hooks/gsd-check-update.js +34 -20
  383. package/hooks/gsd-context-monitor.js +45 -13
  384. package/hooks/gsd-cursor-subagent-start.js +8 -0
  385. package/hooks/gsd-secret-read-guard.js +263 -16
  386. package/hooks/gsd-statusline.js +336 -29
  387. package/hooks/gsd-update-banner.js +8 -0
  388. package/hooks/gsd-windsurf-pre-write.js +11 -2
  389. package/hooks/gsd-workflow-guard.js +5 -4
  390. package/hooks/gsd-worktree-path-guard.js +6 -2
  391. package/hooks/hooks.json +5 -5
  392. package/hooks/lib/cli-exit.js +12 -0
  393. package/hooks/lib/git-probe.js +17 -1
  394. package/hooks/lib/isolation-sentinel.js +2 -2
  395. package/package.json +21 -4
  396. package/scripts/changeset/parse.cjs +52 -4
  397. package/scripts/ci-timeout-report.cjs +770 -4
  398. package/scripts/command-contract-helpers.cjs +12 -8
  399. package/scripts/docs-guard-registry.cjs +6 -0
  400. package/scripts/gen-capability-registry.cjs +7 -1
  401. package/scripts/gen-features.cjs +13 -8
  402. package/scripts/gen-hooks-cli-exit.cjs +12 -28
  403. package/scripts/gen-loop-host-contract.cjs +14 -2
  404. package/scripts/gen-platform-conformance-tier.cjs +187 -1
  405. package/scripts/gen-plugin-skills.cjs +87 -1
  406. package/scripts/gen-research-agents.cjs +24 -31
  407. package/scripts/gen-scripts-cli-exit.cjs +30 -3
  408. package/scripts/gen-test-timings.cjs +32 -7
  409. package/scripts/lib/cli-exit.cjs +12 -0
  410. package/scripts/lib/macos-conformance-tier.generated.cjs +24 -2
  411. package/scripts/lib/ndjson-reporter.cjs +28 -3
  412. package/scripts/lib/platform-conformance-tier.generated.cjs +44 -5
  413. package/scripts/lib/registration-ledger-preload.cjs +155 -0
  414. package/scripts/lib/vendor-bundle.cjs +59 -0
  415. package/scripts/lib/vendor-licenses/saxes-6.0.0.txt +64 -0
  416. package/scripts/lint-allow-test-rule-refs.effective-ceiling.json +1 -1
  417. package/scripts/lint-allow-test-rule-refs.unverified-ceiling.json +1 -1
  418. package/scripts/lint-completion-predicate-drift.cjs +18 -19
  419. package/scripts/lint-descriptions.cjs +7 -3
  420. package/scripts/lint-docs-guard-registration.exempt-baseline.cjs +10 -0
  421. package/scripts/lint-eslint-glob-coverage.allowlist.json +20 -0
  422. package/scripts/lint-frontmatter-fence-drift.cjs +313 -0
  423. package/scripts/lint-frontmatter-scalar-broad-grep.cjs +122 -16
  424. package/scripts/lint-phase-enumeration-drift.cjs +12 -8
  425. package/scripts/lint-phase-id-drift.cjs +29 -0
  426. package/scripts/lint-planning-document-positive-control.cjs +329 -0
  427. package/scripts/lint-response-language-coverage.cjs +3 -0
  428. package/scripts/lint-skill-deps.cjs +7 -3
  429. package/scripts/lint-test-file-count.allowlist.json +11 -1
  430. package/scripts/lint-test-file-count.cjs +34 -1
  431. package/scripts/lint-vendored-deps.cjs +41 -5
  432. package/scripts/lint-workflow-shellcheck-baseline.json +10 -10
  433. package/scripts/mutation-matrix.cjs +53 -6
  434. package/scripts/release-tarball-smoke.cjs +14 -7
  435. package/scripts/require-issue-link-policy.cjs +6 -2
  436. package/scripts/sync-runtime-launcher.cjs +184 -2
  437. package/scripts/verify-npm-publish.cjs +76 -20
  438. package/skills/gsd-add-tests/SKILL.md +6 -1
  439. package/skills/gsd-ai-integration-phase/SKILL.md +6 -1
  440. package/skills/gsd-audit-fix/SKILL.md +5 -0
  441. package/skills/gsd-audit-milestone/SKILL.md +6 -1
  442. package/skills/gsd-autonomous/SKILL.md +5 -0
  443. package/skills/gsd-capture/SKILL.md +8 -4
  444. package/skills/gsd-code-review/SKILL.md +7 -2
  445. package/skills/gsd-complete-milestone/SKILL.md +4 -0
  446. package/skills/gsd-config/SKILL.md +8 -4
  447. package/skills/gsd-debug/SKILL.md +11 -7
  448. package/skills/gsd-discuss-phase/SKILL.md +7 -3
  449. package/skills/gsd-docs-update/SKILL.md +12 -7
  450. package/skills/gsd-eval-review/SKILL.md +6 -1
  451. package/skills/gsd-execute-phase/SKILL.md +12 -7
  452. package/skills/gsd-extract-learnings/SKILL.md +5 -0
  453. package/skills/gsd-fast/SKILL.md +4 -0
  454. package/skills/gsd-forensics/SKILL.md +5 -1
  455. package/skills/gsd-graphify/SKILL.md +10 -6
  456. package/skills/gsd-health/SKILL.md +5 -0
  457. package/skills/gsd-help/SKILL.md +7 -2
  458. package/skills/gsd-import/SKILL.md +7 -3
  459. package/skills/gsd-inbox/SKILL.md +5 -0
  460. package/skills/gsd-ingest-docs/SKILL.md +5 -1
  461. package/skills/gsd-manager/SKILL.md +6 -1
  462. package/skills/gsd-map-codebase/SKILL.md +7 -3
  463. package/skills/gsd-mempalace-capture/SKILL.md +5 -1
  464. package/skills/gsd-mempalace-recall/SKILL.md +5 -1
  465. package/skills/gsd-milestone-summary/SKILL.md +5 -1
  466. package/skills/gsd-mvp-phase/SKILL.md +8 -3
  467. package/skills/gsd-new-milestone/SKILL.md +6 -1
  468. package/skills/gsd-new-project/SKILL.md +5 -0
  469. package/skills/gsd-next/SKILL.md +6 -1
  470. package/skills/gsd-ns-context/SKILL.md +4 -0
  471. package/skills/gsd-ns-ideate/SKILL.md +4 -0
  472. package/skills/gsd-ns-manage/SKILL.md +4 -0
  473. package/skills/gsd-ns-project/SKILL.md +4 -0
  474. package/skills/gsd-ns-review/SKILL.md +4 -0
  475. package/skills/gsd-ns-workflow/SKILL.md +4 -0
  476. package/skills/gsd-onboard/SKILL.md +6 -1
  477. package/skills/gsd-pause-work/SKILL.md +5 -1
  478. package/skills/gsd-phase/SKILL.md +8 -4
  479. package/skills/gsd-plan-phase/SKILL.md +6 -1
  480. package/skills/gsd-plan-review-convergence/SKILL.md +5 -1
  481. package/skills/gsd-pr-branch/SKILL.md +4 -0
  482. package/skills/gsd-profile-user/SKILL.md +5 -1
  483. package/skills/gsd-progress/SKILL.md +6 -1
  484. package/skills/gsd-quick/SKILL.md +16 -10
  485. package/skills/gsd-quick-batch/SKILL.md +20 -8
  486. package/skills/gsd-review/SKILL.md +5 -1
  487. package/skills/gsd-review-backlog/SKILL.md +3 -2
  488. package/skills/gsd-secure-phase/SKILL.md +6 -1
  489. package/skills/gsd-ship/SKILL.md +5 -0
  490. package/skills/gsd-sketch/SKILL.md +7 -2
  491. package/skills/gsd-spec-phase/SKILL.md +5 -1
  492. package/skills/gsd-spike/SKILL.md +8 -3
  493. package/skills/gsd-surface/SKILL.md +5 -1
  494. package/skills/gsd-thread/SKILL.md +4 -0
  495. package/skills/gsd-ui-phase/SKILL.md +6 -1
  496. package/skills/gsd-ui-review/SKILL.md +6 -1
  497. package/skills/gsd-ultraplan-phase/SKILL.md +5 -1
  498. package/skills/gsd-undo/SKILL.md +5 -1
  499. package/skills/gsd-update/SKILL.md +6 -2
  500. package/skills/gsd-validate-phase/SKILL.md +6 -1
  501. package/skills/gsd-verify-work/SKILL.md +6 -1
  502. package/skills/gsd-workspace/SKILL.md +7 -3
  503. package/skills/gsd-workstreams/SKILL.md +6 -6
  504. package/vscode/package.json +1 -1
  505. package/gsd-core/workflows/execute-phase/steps/stale-reverification.md +0 -24
@@ -25,6 +25,9 @@ const path = require('node:path');
25
25
 
26
26
  const { PROFILES } = require('./research-profiles.cjs');
27
27
  const { ExitError, runMain } = require('./lib/cli-exit.cjs');
28
+ // The one frontmatter fence owner (src/frontmatter-fence.cts, built by build:lib).
29
+ // This dev-time script runs after the build (manually, and from the tests).
30
+ const { locateFrontmatterFence } = require('../gsd-core/bin/lib/frontmatter-fence.cjs');
28
31
 
29
32
  const ROOT = path.resolve(__dirname, '..');
30
33
  const AGENTS_DIR = path.join(ROOT, 'agents');
@@ -41,12 +44,13 @@ const AGENTS_DIR = path.join(ROOT, 'agents');
41
44
  * We read the CURRENT commented-hooks block from the agent file and preserve it
42
45
  * byte-for-byte; only name/description/tools/color are regenerated.
43
46
  */
44
- function buildFrontmatter(profile, existingFrontmatter) {
45
- // Extract the commented hooks section from the existing frontmatter, if any.
46
- // The hooks block starts at `# hooks:` and runs to (but not including) the
47
- // closing `---`. In the committed files there is NO blank line between
48
- // `color:` and `# hooks:`, so we append it directly after the color line's `\n`.
49
- const hooksMatch = existingFrontmatter.match(/(# hooks:[\s\S]*?)(?=\n---)/);
47
+ function buildFrontmatter(profile, existingRegion) {
48
+ // Extract the commented hooks section from the existing frontmatter region
49
+ // (the YAML text between the fences), if any. The hooks block starts at
50
+ // `# hooks:` and runs to the end of the region — the closing `---` follows it.
51
+ // In the committed files there is NO blank line between `color:` and
52
+ // `# hooks:`, so we append it directly after the color line's `\n`.
53
+ const hooksMatch = existingRegion.match(/(# hooks:[\s\S]*)$/);
50
54
  // hooksSuffix: if present, the block followed by a newline so `---` is on its own line;
51
55
  // if absent, empty string (the closing `---` follows directly after color's `\n`).
52
56
  const hooksSuffix = hooksMatch ? hooksMatch[1] + '\n' : '';
@@ -67,37 +71,26 @@ function buildFrontmatter(profile, existingFrontmatter) {
67
71
  /**
68
72
  * Parse a .md file and return { frontmatterRaw, body, frontmatterFields }.
69
73
  *
70
- * frontmatterRaw: the raw text between the first and second `---` delimiters (exclusive)
71
- * body: everything after the closing `---\n`
74
+ * frontmatterRaw: the YAML text between the opening and closing fences (exclusive)
75
+ * fullFrontmatter: the block from the opening fence through the closing fence line
76
+ * body: everything after the closing fence line's line ending
72
77
  * frontmatterFields: { name, description, color, tools }
78
+ *
79
+ * The block is the one the one fence owner finds (found while implementing #5105):
80
+ * it opens at byte 0 (after a BOM), exactly as the runtime that loads the agent reads it.
73
81
  */
74
82
  function parseAgentFile(filePath) {
75
83
  const raw = fs.readFileSync(filePath, 'utf8');
76
84
 
77
- // The frontmatter is between the first `---` line and the next `---` line.
78
- const lines = raw.split('\n');
79
- let start = -1;
80
- let end = -1;
81
- for (let i = 0; i < lines.length; i++) {
82
- if (lines[i].trim() === '---') {
83
- if (start === -1) {
84
- start = i;
85
- } else {
86
- end = i;
87
- break;
88
- }
89
- }
90
- }
91
-
92
- if (start === -1 || end === -1) {
85
+ const fence = locateFrontmatterFence(raw);
86
+ if (!fence || !fence.closed) {
93
87
  throw new Error('No valid frontmatter delimiters found in ' + filePath);
94
88
  }
95
89
 
96
- const frontmatterLines = lines.slice(start + 1, end);
97
- const frontmatterRaw = frontmatterLines.join('\n');
98
- // body includes the closing `---` line and everything after
99
- const fullFrontmatter = lines.slice(start, end + 1).join('\n');
100
- const body = lines.slice(end + 1).join('\n');
90
+ const frontmatterRaw = raw.slice(fence.openEnd, fence.bodyEnd);
91
+ const frontmatterLines = frontmatterRaw.split(/\r?\n/);
92
+ const fullFrontmatter = raw.slice(fence.bom.length, fence.closingFenceEnd);
93
+ const body = raw.slice(fence.closingFenceEnd).replace(/^\r?\n/, '');
101
94
 
102
95
  const fields = {};
103
96
  // Parse simple key: value pairs (not nested YAML, no multi-line values here)
@@ -214,9 +207,9 @@ function runCheck() {
214
207
  */
215
208
  function writeAgent(profile) {
216
209
  const agentPath = path.join(AGENTS_DIR, profile.name + '.md');
217
- const { fullFrontmatter, body } = parseAgentFile(agentPath);
210
+ const { frontmatterRaw, body } = parseAgentFile(agentPath);
218
211
 
219
- const newFrontmatter = buildFrontmatter(profile, fullFrontmatter);
212
+ const newFrontmatter = buildFrontmatter(profile, frontmatterRaw);
220
213
  const newContent = newFrontmatter + '\n' + body;
221
214
 
222
215
  fs.writeFileSync(agentPath, newContent, 'utf8');
@@ -65,15 +65,40 @@ const BANNER = [
65
65
  '',
66
66
  ].join('\n');
67
67
 
68
- /** Compile the whole project to a throwaway outDir so the work tree is untouched. */
68
+ /**
69
+ * Compile ONLY src/cli-exit.cts (and whatever it imports — tsc follows
70
+ * `./exit-code-registry.cjs` on its own) to a throwaway outDir, so the work
71
+ * tree is untouched. A whole-project `-p tsconfig.build.json` type-checks and
72
+ * emits every .cts file in src/ under a fixed COMPILE_TIMEOUT_MS ceiling; on a
73
+ * CPU-contended shared bench that whole-project compile can exceed the
74
+ * ceiling and get killed even though the one file this script actually needs
75
+ * compiles in a fraction of the time. A throwaway tsconfig that `extends`
76
+ * tsconfig.build.json but overrides `files`/`include` to name only
77
+ * cli-exit.cts keeps every compiler option (target, strict, rootDir, etc.)
78
+ * while scoping the type-check + emit to that file's own import closure.
79
+ */
69
80
  function compileToTemp() {
70
81
  const tmp = fs.mkdtempSync(path.join(os.tmpdir(), 'gsd-scripts-cli-exit-'));
82
+ const scopedTsconfigPath = path.join(tmp, 'tsconfig.scoped.json');
71
83
  try {
84
+ const scopedTsconfig = {
85
+ extends: path.join(REPO_ROOT, 'tsconfig.build.json'),
86
+ // typeRoots must be pinned to the real repo's node_modules/@types: tsc
87
+ // resolves a bare "types": ["node"] by walking up from the config
88
+ // file's own directory, and our scoped tsconfig lives outside the repo
89
+ // tree (in the throwaway tmp dir), so without this it cannot find
90
+ // @types/node at all.
91
+ compilerOptions: { typeRoots: [path.join(REPO_ROOT, 'node_modules', '@types')] },
92
+ files: [path.join(REPO_ROOT, 'src', 'cli-exit.cts')],
93
+ include: [],
94
+ };
95
+ fs.writeFileSync(scopedTsconfigPath, JSON.stringify(scopedTsconfig, null, 2), 'utf8');
96
+
72
97
  execFileSync(
73
98
  process.execPath,
74
99
  [
75
100
  path.join(REPO_ROOT, 'node_modules', 'typescript', 'bin', 'tsc'),
76
- '-p', path.join(REPO_ROOT, 'tsconfig.build.json'),
101
+ '-p', scopedTsconfigPath,
77
102
  '--outDir', tmp,
78
103
  // A throwaway outDir must not reuse the in-tree incremental state, or
79
104
  // tsc skips emit for files it believes are already current.
@@ -87,6 +112,8 @@ function compileToTemp() {
87
112
  fs.rmSync(tmp, { recursive: true, force: true });
88
113
  const detail = [err.stdout, err.stderr].filter(Boolean).join('\n').trim();
89
114
  return { ok: false, detail };
115
+ } finally {
116
+ fs.rmSync(scopedTsconfigPath, { force: true });
90
117
  }
91
118
  }
92
119
 
@@ -182,4 +209,4 @@ function main() {
182
209
 
183
210
  if (require.main === module) process.exitCode = main();
184
211
 
185
- module.exports = { REASON, buildExpectedContent, OUTPUT_PATH, BANNER };
212
+ module.exports = { REASON, buildExpectedContent, compileToTemp, OUTPUT_PATH, BANNER };
@@ -19,6 +19,9 @@
19
19
  // node scripts/gen-test-timings.cjs <events.jsonl> [<events.jsonl> ...]
20
20
  // node scripts/gen-test-timings.cjs ~/.local/state/gsd-test/runs/*/test-events-*.jsonl
21
21
  // node scripts/gen-test-timings.cjs events.jsonl --out tests/test-timings.json
22
+ // node scripts/gen-test-timings.cjs --platform win32 test-timings-windows-shard*.jsonl
23
+ // (#5071: the per-shard exports CI uploads from its Windows conformance
24
+ // jobs -> tests/test-timings.win32.json, preferred by run-tests.cjs on win32)
22
25
  //
23
26
  // When several streams are supplied (multiple lanes, e.g. node22 + node24), a
24
27
  // file's recorded time is the MAX across them, not the mean: the packer exists
@@ -28,9 +31,9 @@
28
31
  // The table is ADVISORY and deliberately un-gated — there is no `--check` mode
29
32
  // and no CI lint that fails on staleness, because timing data legitimately
30
33
  // varies run to run. A file missing from the table falls back to the table's
31
- // median weight, so a stale table degrades chunk BALANCE gracefully instead of
32
- // failing the build. Regenerate it when the suite's cost profile has visibly
33
- // drifted, not on a schedule.
34
+ // mean weight (see makeFileWeigher in run-tests.cjs), so a stale table
35
+ // degrades chunk BALANCE gracefully instead of failing the build. Regenerate
36
+ // it when the suite's cost profile has visibly drifted, not on a schedule.
34
37
  'use strict';
35
38
 
36
39
  const fs = require('fs');
@@ -40,12 +43,32 @@ const { ExitError, runMain } = require('./lib/cli-exit.cjs');
40
43
  const DEFAULT_OUT = join(__dirname, '..', 'tests', 'test-timings.json');
41
44
  const SCHEMA_VERSION = 1;
42
45
 
46
+ // #5071: `--platform <p>` writes the table measured ON that platform, which
47
+ // scripts/run-tests.cjs prefers there (see its makeFileWeigher). The default
48
+ // path must match run-tests.cjs's platformTimingsPath() —
49
+ // tests/run-tests-harness.test.cjs pins the two together. A closed set, in
50
+ // exactly Node's own `process.platform` spelling, because the value becomes
51
+ // part of a filename the runner looks up by that spelling.
52
+ const PLATFORMS = ['win32', 'darwin', 'linux'];
53
+ function platformOut(platform) {
54
+ return join(__dirname, '..', 'tests', `test-timings.${platform}.json`);
55
+ }
56
+
43
57
  function parseArgs(argv) {
44
58
  const inputs = [];
45
- let out = DEFAULT_OUT;
59
+ let out = null;
60
+ let platform = null;
46
61
  for (let i = 0; i < argv.length; i++) {
47
62
  const arg = argv[i];
48
- if (arg === '--out') {
63
+ if (arg === '--platform' || arg.startsWith('--platform=')) {
64
+ if (platform !== null) return { error: 'duplicate --platform flag' };
65
+ const value = arg === '--platform' ? argv[++i] : arg.slice('--platform='.length);
66
+ if (!value || value.startsWith('-')) return { error: `--platform requires one of: ${PLATFORMS.join(', ')}` };
67
+ if (!PLATFORMS.includes(value)) {
68
+ return { error: `unknown --platform "${value}" (expected one of: ${PLATFORMS.join(', ')})` };
69
+ }
70
+ platform = value;
71
+ } else if (arg === '--out') {
49
72
  const value = argv[++i];
50
73
  if (!value) return { error: '--out requires a path' };
51
74
  out = value;
@@ -60,9 +83,10 @@ function parseArgs(argv) {
60
83
  }
61
84
  }
62
85
  if (inputs.length === 0) {
63
- return { error: 'usage: gen-test-timings.cjs <reporter-events.jsonl> [...] [--out <path>]' };
86
+ return { error: 'usage: gen-test-timings.cjs <reporter-events.jsonl> [...] [--platform <win32|darwin|linux>] [--out <path>]' };
64
87
  }
65
- return { inputs, out };
88
+ if (out === null) out = platform ? platformOut(platform) : DEFAULT_OUT;
89
+ return { inputs, out, platform };
66
90
  }
67
91
 
68
92
  // Fold one reporter event stream into `acc`, keeping the MAX duration seen for
@@ -180,6 +204,7 @@ function main() {
180
204
  const payload = {
181
205
  schema_version: SCHEMA_VERSION,
182
206
  generated_by: 'scripts/gen-test-timings.cjs',
207
+ ...(parsed.platform ? { platform: parsed.platform } : {}),
183
208
  unit: 'ms',
184
209
  sources: sources.sort(),
185
210
  file_count: acc.size,
@@ -183,6 +183,17 @@ function setPendingOutcome(v) {
183
183
  function getPendingOutcome() {
184
184
  return globalThis[PENDING_OUTCOME_KEY];
185
185
  }
186
+ /**
187
+ * Declare the outcome a void-returning `main()` ends with (#5170, ADR-5057 §4): writes the
188
+ * pending-outcome cell that `runMain` projects. Validates `name` is an outcome
189
+ * `projectOutcome` accepts (PASS, FAIL or a registered name) and THROWS otherwise, so a typo'd
190
+ * name fails at the declaration rather than at process exit. Call it AFTER `output()`, which
191
+ * rewrites the cell on every call. `output()` and this are the only writers of the cell.
192
+ */
193
+ function declareOutcome(name) {
194
+ projectOutcome(name, 'v1');
195
+ setPendingOutcome(name);
196
+ }
186
197
  const EXIT_CONTRACT_FLAG_PREFIX = '--exit-contract=';
187
198
  /** Scan argv for the FIRST `--exit-contract=<value>` token; undefined if absent. */
188
199
  function findExitContractFlag(argv) {
@@ -555,4 +566,5 @@ module.exports = {
555
566
  terminateNow,
556
567
  setPendingOutcome,
557
568
  getPendingOutcome,
569
+ declareOutcome,
558
570
  };
@@ -6,6 +6,7 @@
6
6
 
7
7
  module.exports = {
8
8
  MACOS_CONFORMANCE_TIER_FILES: [
9
+ "tests/active-workstream-store.unit.test.cjs",
9
10
  "tests/adr-612-bracket-phase-counting.test.cjs",
10
11
  "tests/adr-index-gate.test.cjs",
11
12
  "tests/adr-parser.property.test.cjs",
@@ -32,6 +33,7 @@ module.exports = {
32
33
  "tests/changeset-parse.test.cjs",
33
34
  "tests/check-contract-drift.test.cjs",
34
35
  "tests/check-predicate.test.cjs",
36
+ "tests/check-router-cutover-equivalence.test.cjs",
35
37
  "tests/check-ui-plan-gate.test.cjs",
36
38
  "tests/check-ui-safety-gate.test.cjs",
37
39
  "tests/check-update-config-dir.test.cjs",
@@ -44,7 +46,7 @@ module.exports = {
44
46
  "tests/codex-config-hooks.test.cjs",
45
47
  "tests/codex-config-install.test.cjs",
46
48
  "tests/codex-config.test.cjs",
47
- "tests/commands.test.cjs",
49
+ "tests/commands.platform.test.cjs",
48
50
  "tests/commit-docs-bypass.test.cjs",
49
51
  "tests/commit-files-deletion.test.cjs",
50
52
  "tests/commit-files-pathspec.test.cjs",
@@ -61,6 +63,7 @@ module.exports = {
61
63
  "tests/default-flip-documentation-lint.test.cjs",
62
64
  "tests/discuss-phase-power.test.cjs",
63
65
  "tests/docs-parity-live-registry.test.cjs",
66
+ "tests/drift-whole-change-set.test.cjs",
64
67
  "tests/effort-surface-axis.test.cjs",
65
68
  "tests/effort-sync-installed-runtime.test.cjs",
66
69
  "tests/emitted-attribution.test.cjs",
@@ -75,12 +78,18 @@ module.exports = {
75
78
  "tests/features-index-gate.test.cjs",
76
79
  "tests/frontmatter.unit.test.cjs",
77
80
  "tests/gap-checker.property.test.cjs",
81
+ "tests/gate-api-coverage-verify-pre-escape.test.cjs",
82
+ "tests/gate-codebase-drift.unit.test.cjs",
83
+ "tests/gate-tdd-red-evidence-containment.test.cjs",
84
+ "tests/gate-ui-plan.unit.test.cjs",
85
+ "tests/gate-verify-command-paths.unit.test.cjs",
78
86
  "tests/gemini-runtime-removed.test.cjs",
79
87
  "tests/gen-context-index.test.cjs",
80
88
  "tests/gen-section-manifest.test.cjs",
81
89
  "tests/git-base-branch.test.cjs",
82
90
  "tests/graphify-query.test.cjs",
83
91
  "tests/graphify-visualization.test.cjs",
92
+ "tests/gsd-agent-isolation-guard.test.cjs",
84
93
  "tests/gsd-secret-read-guard.test.cjs",
85
94
  "tests/gsd-settings-advanced.test.cjs",
86
95
  "tests/gsd-statusline.test.cjs",
@@ -96,7 +105,6 @@ module.exports = {
96
105
  "tests/hooks-opt-in.test.cjs",
97
106
  "tests/host-integration.test.cjs",
98
107
  "tests/init-manager.test.cjs",
99
- "tests/init.test.cjs",
100
108
  "tests/install-minimal-hooks.test.cjs",
101
109
  "tests/install-path-detection.test.cjs",
102
110
  "tests/install-regressions.test.cjs",
@@ -115,9 +123,11 @@ module.exports = {
115
123
  "tests/issue-version-gate.test.cjs",
116
124
  "tests/kimi-upgrades.test.cjs",
117
125
  "tests/lint-docs-command-form.test.cjs",
126
+ "tests/lint-frontmatter-scalar-broad-grep.test.cjs",
118
127
  "tests/lint-retired-runtime-name.test.cjs",
119
128
  "tests/lint-workflow-shellcheck-fetch.test.cjs",
120
129
  "tests/list-seeds.test.cjs",
130
+ "tests/markdown-sectionizer-xml-tags.property.test.cjs",
121
131
  "tests/markdown-sectionizer.test.cjs",
122
132
  "tests/mcp-catalog.test.cjs",
123
133
  "tests/milestone-archive.test.cjs",
@@ -133,7 +143,11 @@ module.exports = {
133
143
  "tests/nsegment-phase-grammar.test.cjs",
134
144
  "tests/observability/event.test.cjs",
135
145
  "tests/onboard-command.test.cjs",
146
+ "tests/opencode-generations.smoke.test.cjs",
147
+ "tests/opencode-install-notices.test.cjs",
148
+ "tests/opencode-parity-hooks.test.cjs",
136
149
  "tests/opencode-plugin-adapter.test.cjs",
150
+ "tests/opencode-uninstall-roundtrip.test.cjs",
137
151
  "tests/pause-work-context-detection.test.cjs",
138
152
  "tests/pause-work-improvements.test.cjs",
139
153
  "tests/perf-317-context-monitor-fs.test.cjs",
@@ -142,6 +156,8 @@ module.exports = {
142
156
  "tests/phase-id-drift-guard.test.cjs",
143
157
  "tests/phase-id.test.cjs",
144
158
  "tests/phase-locator.test.cjs",
159
+ "tests/phase-status.test.cjs",
160
+ "tests/phase.platform.test.cjs",
145
161
  "tests/phase.test.cjs",
146
162
  "tests/plan-count-single-owner.test.cjs",
147
163
  "tests/plan-document.test.cjs",
@@ -162,6 +178,7 @@ module.exports = {
162
178
  "tests/profile-output.test.cjs",
163
179
  "tests/profile-pipeline.test.cjs",
164
180
  "tests/project-root.test.cjs",
181
+ "tests/quick-batch-command-router.stdin.test.cjs",
165
182
  "tests/quick-batch.test.cjs",
166
183
  "tests/quick-branching.test.cjs",
167
184
  "tests/quick-research.test.cjs",
@@ -183,6 +200,7 @@ module.exports = {
183
200
  "tests/roadmap-phase-fallback.test.cjs",
184
201
  "tests/roadmap-upgrade-bracket.test.cjs",
185
202
  "tests/roadmap.test.cjs",
203
+ "tests/run-tests-accounting.test.cjs",
186
204
  "tests/run-tests-harness.test.cjs",
187
205
  "tests/runtime-artifact-layout.test.cjs",
188
206
  "tests/runtime-identity.test.cjs",
@@ -196,11 +214,14 @@ module.exports = {
196
214
  "tests/spawn-liveness-banner.test.cjs",
197
215
  "tests/state-document.test.cjs",
198
216
  "tests/state-transition.test.cjs",
217
+ "tests/state.platform.test.cjs",
199
218
  "tests/state.test.cjs",
200
219
  "tests/todos-workstream-scope.test.cjs",
201
220
  "tests/tracer-bullet.test.cjs",
221
+ "tests/uat-complete-session.test.cjs",
202
222
  "tests/uat-predicate.test.cjs",
203
223
  "tests/uat.test.cjs",
224
+ "tests/ui-auditor-screenshot-block.test.cjs",
204
225
  "tests/ui-interaction-capture.test.cjs",
205
226
  "tests/ui-safety-gate.test.cjs",
206
227
  "tests/ui-spec-inventory-provenance.test.cjs",
@@ -209,6 +230,7 @@ module.exports = {
209
230
  "tests/unusable-input.test.cjs",
210
231
  "tests/update-custom-backup.test.cjs",
211
232
  "tests/user-artifact-staging.test.cjs",
233
+ "tests/verification-append-audit.test.cjs",
212
234
  "tests/verification-overrides.test.cjs",
213
235
  "tests/verification-status.test.cjs",
214
236
  "tests/verify-archive-dirs-live-path.test.cjs",
@@ -50,8 +50,9 @@
50
50
  // repo's `engines.node` requires >=24.0.0 (package.json), where both
51
51
  // contracts have been stable since Node 20.
52
52
  //
53
- // Kept intentionally tiny: only the five event types run-tests.cjs needs are
54
- // handled — `test:enqueue`/`test:dequeue` (emitted by the RUNNER as it queues
53
+ // Kept intentionally tiny: only the event types run-tests.cjs needs are
54
+ // handled — per-file `test:summary` (#5071, see the loop) plus these five:
55
+ // `test:enqueue`/`test:dequeue` (emitted by the RUNNER as it queues
55
56
  // and begins each spawned test-file child, independent of whether anything
56
57
  // inside that file ever completes) plus `test:start`/`test:pass`/`test:fail`
57
58
  // (emitted per-subtest, once the child reports it). `test:dequeue` is the
@@ -94,13 +95,19 @@ module.exports = async function ndjsonEventReporter(source) {
94
95
  event.type === 'test:pass' ||
95
96
  event.type === 'test:fail'
96
97
  ) {
97
- const { file, name, nesting, testNumber } = event.data || {};
98
+ const { file, name, nesting, testNumber, details } = event.data || {};
99
+ // #4031: `kind` is node:test's `details.type` ('suite' for a suite,
100
+ // otherwise a test). run-tests.cjs's per-chunk accounting counts the
101
+ // pass/fail events that are NOT suites and compares them with the
102
+ // registration ledger (scripts/lib/registration-ledger-preload.cjs).
103
+ const kind = details && typeof details.type === 'string' ? details.type : undefined;
98
104
  const line = `${JSON.stringify({
99
105
  type: event.type,
100
106
  file,
101
107
  name,
102
108
  nesting,
103
109
  testNumber,
110
+ kind,
104
111
  ts: Date.now(),
105
112
  })}\n`;
106
113
  try {
@@ -109,6 +116,24 @@ module.exports = async function ndjsonEventReporter(source) {
109
116
  // Best-effort: a write failure here (e.g. the events dir vanished)
110
117
  // must never crash the test run this reporter is only observing.
111
118
  }
119
+ } else if (event.type === 'test:summary' && typeof (event.data || {}).file === 'string') {
120
+ // #5071: node:test emits one `test:summary` per test FILE (its
121
+ // `duration_ms` is that file's wall-clock) plus a run-level one with no
122
+ // `file`. Only the per-file ones are recorded: run-tests.cjs exports
123
+ // them, when asked, as the raw input for a per-platform timing table
124
+ // (scripts/gen-test-timings.cjs --platform). The run-level summary is
125
+ // not a file measurement and is skipped here.
126
+ const line = `${JSON.stringify({
127
+ type: event.type,
128
+ file: event.data.file,
129
+ duration_ms: event.data.duration_ms,
130
+ ts: Date.now(),
131
+ })}\n`;
132
+ try {
133
+ require('fs').appendFileSync(eventsPath, line);
134
+ } catch {
135
+ // Best-effort, as above.
136
+ }
112
137
  }
113
138
  }
114
139
  // Falls through to an implicit `return undefined` (nully): this reporter is
@@ -14,7 +14,9 @@ module.exports = {
14
14
  "tests/assumption-delta-checkpoint-e2e.test.cjs",
15
15
  "tests/assumption-delta.test.cjs",
16
16
  "tests/audit-command-cutover.test.cjs",
17
+ "tests/audit-workstream-layouts.test.cjs",
17
18
  "tests/augment-upgrades.test.cjs",
19
+ "tests/blocking-guard-budget-parity.test.cjs",
18
20
  "tests/broken-windows.test.cjs",
19
21
  "tests/capability-cli.test.cjs",
20
22
  "tests/capability-command-dispatch.test.cjs",
@@ -32,9 +34,12 @@ module.exports = {
32
34
  "tests/check-gap-analysis-plan-post-e2e.test.cjs",
33
35
  "tests/check-glossary-refs.test.cjs",
34
36
  "tests/check-predicate.test.cjs",
37
+ "tests/check-router-cutover-equivalence.test.cjs",
38
+ "tests/check-router-gate-boundaries.test.cjs",
35
39
  "tests/check-tdd-review-checkpoint-e2e.test.cjs",
36
40
  "tests/check-ui-safety-gate.test.cjs",
37
41
  "tests/check-update-config-dir.test.cjs",
42
+ "tests/check-update-fail-open.test.cjs",
38
43
  "tests/chunked-planning-parallel.test.cjs",
39
44
  "tests/ci-docs-guard-registry.test.cjs",
40
45
  "tests/ci-rebase-check.test.cjs",
@@ -47,13 +52,15 @@ module.exports = {
47
52
  "tests/code-review-pipeline-regression.test.cjs",
48
53
  "tests/code-review-tier3-files-override-scoping.test.cjs",
49
54
  "tests/code-review.test.cjs",
55
+ "tests/code-reviewer-contribution.test.cjs",
50
56
  "tests/codex-config-agents.test.cjs",
51
57
  "tests/codex-config-hooks.test.cjs",
52
58
  "tests/codex-config-install.test.cjs",
53
59
  "tests/codex-config.test.cjs",
54
60
  "tests/codex-inherit-smoke.test.cjs",
61
+ "tests/codex-windows-shim-node-resolution.test.cjs",
55
62
  "tests/command-routing-hub.test.cjs",
56
- "tests/commands.test.cjs",
63
+ "tests/commands.platform.test.cjs",
57
64
  "tests/commit-files-deletion.test.cjs",
58
65
  "tests/commit-files-pathspec.test.cjs",
59
66
  "tests/commonjs-marker.test.cjs",
@@ -63,17 +70,22 @@ module.exports = {
63
70
  "tests/config-get-default.test.cjs",
64
71
  "tests/config-loader.test.cjs",
65
72
  "tests/config-schema.property.test.cjs",
66
- "tests/config.test.cjs",
73
+ "tests/config.platform.test.cjs",
67
74
  "tests/configured-entrypoint-validation.test.cjs",
75
+ "tests/context-drift.test.cjs",
76
+ "tests/context-monitor-host-contract.test.cjs",
68
77
  "tests/copilot-install.test.cjs",
69
78
  "tests/copilot-upgrades.test.cjs",
70
79
  "tests/core-utils.test.cjs",
71
80
  "tests/cursor-hook-workspace-roots.test.cjs",
72
81
  "tests/cursor-hooks.test.cjs",
73
82
  "tests/cursor-subagent-isolation.test.cjs",
83
+ "tests/debug-session-management.test.cjs",
74
84
  "tests/dispatch-identity.test.cjs",
75
85
  "tests/dispatcher.test.cjs",
76
86
  "tests/drift-detection.test.cjs",
87
+ "tests/drift-whole-change-set.test.cjs",
88
+ "tests/effort-local-install.test.cjs",
77
89
  "tests/effort-surface-axis.test.cjs",
78
90
  "tests/effort-sync-installed-runtime.test.cjs",
79
91
  "tests/emitted-ack-trailer.test.cjs",
@@ -95,6 +107,16 @@ module.exports = {
95
107
  "tests/features-index-gate.test.cjs",
96
108
  "tests/frontmatter.test.cjs",
97
109
  "tests/gap-checker.property.test.cjs",
110
+ "tests/gate-api-coverage-verify-pre-escape.test.cjs",
111
+ "tests/gate-consumer-exit-awareness.test.cjs",
112
+ "tests/gate-decision-coverage-verify-stderr.test.cjs",
113
+ "tests/gate-exit.test.cjs",
114
+ "tests/gate-tdd-red-evidence-containment.test.cjs",
115
+ "tests/gate-tdd-review-checkpoint-hardening.test.cjs",
116
+ "tests/gate-tdd-review-checkpoint.unit.test.cjs",
117
+ "tests/gate-ui-plan.unit.test.cjs",
118
+ "tests/gate-ui-safety.unit.test.cjs",
119
+ "tests/gate-verify-command-paths.unit.test.cjs",
98
120
  "tests/gemini-runtime-removed.test.cjs",
99
121
  "tests/gen-context-index.test.cjs",
100
122
  "tests/gen-health-docs.test.cjs",
@@ -118,12 +140,12 @@ module.exports = {
118
140
  "tests/helpers-cleanup.test.cjs",
119
141
  "tests/helpers-process-isolation.test.cjs",
120
142
  "tests/hermes-skills-migration.test.cjs",
143
+ "tests/hook-activation-probe.test.cjs",
121
144
  "tests/hooks-commonjs-marker.test.cjs",
122
145
  "tests/hooks-crash-policy.test.cjs",
123
146
  "tests/hooks-opt-in.test.cjs",
124
147
  "tests/host-integration.test.cjs",
125
148
  "tests/init-manager.test.cjs",
126
- "tests/init.test.cjs",
127
149
  "tests/install-minimal-hooks.test.cjs",
128
150
  "tests/install-nested-layout.test.cjs",
129
151
  "tests/install-path-detection.test.cjs",
@@ -145,6 +167,7 @@ module.exports = {
145
167
  "tests/kimi-agent-converter.test.cjs",
146
168
  "tests/kimi-upgrades.test.cjs",
147
169
  "tests/kimi-variant-disambiguation.test.cjs",
170
+ "tests/launcher-homes-derivation.test.cjs",
148
171
  "tests/lint-phase-arg-assignment.test.cjs",
149
172
  "tests/lint-workflow-shellcheck-fetch.test.cjs",
150
173
  "tests/live-config-guard.test.cjs",
@@ -170,12 +193,19 @@ module.exports = {
170
193
  "tests/no-unbounded-dirname-walk.rule.test.cjs",
171
194
  "tests/no-unbounded-spawn.test.cjs",
172
195
  "tests/no-unguarded-nonportable-exec.rule.test.cjs",
196
+ "tests/node-compile-cache.test.cjs",
173
197
  "tests/npm-audit-baseline.test.cjs",
174
198
  "tests/npm-integrity-gate.test.cjs",
175
199
  "tests/nsegment-phase-grammar.test.cjs",
176
200
  "tests/onboard-command.test.cjs",
177
201
  "tests/opencode-command-dir-plural.test.cjs",
202
+ "tests/opencode-config-jsonc.test.cjs",
203
+ "tests/opencode-generations.smoke.test.cjs",
204
+ "tests/opencode-install-notices.test.cjs",
205
+ "tests/opencode-parity-hooks.test.cjs",
178
206
  "tests/opencode-plugin-adapter.test.cjs",
207
+ "tests/opencode-statusline-plugin.test.cjs",
208
+ "tests/opencode-uninstall-roundtrip.test.cjs",
179
209
  "tests/overlay-repo-helpers.test.cjs",
180
210
  "tests/packaging-shipped-scripts-require-only-shipped.test.cjs",
181
211
  "tests/path-replacement.test.cjs",
@@ -185,7 +215,7 @@ module.exports = {
185
215
  "tests/phase-completion-single-owner.test.cjs",
186
216
  "tests/phase-estimation.test.cjs",
187
217
  "tests/phase-locator.test.cjs",
188
- "tests/phase.test.cjs",
218
+ "tests/phase.platform.test.cjs",
189
219
  "tests/phase6-capstone-conformance.test.cjs",
190
220
  "tests/pi-config-dir-env-override.test.cjs",
191
221
  "tests/plan-count-single-owner.test.cjs",
@@ -212,6 +242,7 @@ module.exports = {
212
242
  "tests/profile-pipeline.test.cjs",
213
243
  "tests/prohibition-enforcement.test.cjs",
214
244
  "tests/project-root.test.cjs",
245
+ "tests/quick-batch-command-router.stdin.test.cjs",
215
246
  "tests/quick-batch.test.cjs",
216
247
  "tests/quick-branching.test.cjs",
217
248
  "tests/quick-research.test.cjs",
@@ -238,15 +269,18 @@ module.exports = {
238
269
  "tests/roadmap-parser.test.cjs",
239
270
  "tests/roadmap-upgrade-bracket.test.cjs",
240
271
  "tests/roadmap.test.cjs",
272
+ "tests/run-tests-accounting.test.cjs",
241
273
  "tests/run-tests-harness.test.cjs",
242
274
  "tests/run-tests-temp-root.test.cjs",
243
275
  "tests/run-with-timeout.test.cjs",
244
276
  "tests/runtime-artifact-layout-surface.test.cjs",
245
277
  "tests/runtime-artifact-layout.test.cjs",
246
278
  "tests/runtime-converters.test.cjs",
279
+ "tests/runtime-descriptor-owner.test.cjs",
247
280
  "tests/runtime-homes-descriptor-drive.test.cjs",
248
281
  "tests/runtime-identity.test.cjs",
249
282
  "tests/runtime-launcher-parity.test.cjs",
283
+ "tests/schema-drift.test.cjs",
250
284
  "tests/security.test.cjs",
251
285
  "tests/settings-jsonc.test.cjs",
252
286
  "tests/sh-hook-paths.test.cjs",
@@ -258,10 +292,12 @@ module.exports = {
258
292
  "tests/skill-manifest.test.cjs",
259
293
  "tests/slug-derivation-drift-guard.test.cjs",
260
294
  "tests/state-todos-render.test.cjs",
261
- "tests/state.test.cjs",
295
+ "tests/state.platform.test.cjs",
262
296
  "tests/teams-status.test.cjs",
263
297
  "tests/test-gate-watch-mode.test.cjs",
264
298
  "tests/todos-workstream-scope.test.cjs",
299
+ "tests/uat-complete-session.test.cjs",
300
+ "tests/ui-auditor-screenshot-block.test.cjs",
265
301
  "tests/ui-interaction-capture.test.cjs",
266
302
  "tests/undo-commit-selection-4465.test.cjs",
267
303
  "tests/undo-commit-selection.test.cjs",
@@ -270,9 +306,12 @@ module.exports = {
270
306
  "tests/unusable-input.test.cjs",
271
307
  "tests/update-custom-backup.test.cjs",
272
308
  "tests/user-artifact-staging.test.cjs",
309
+ "tests/verification-append-audit.test.cjs",
273
310
  "tests/verification-status.test.cjs",
274
311
  "tests/verify-archive-dirs-live-path.test.cjs",
275
312
  "tests/verify-command-grounding.test.cjs",
313
+ "tests/verify-lifecycle-writes-e2e.test.cjs",
314
+ "tests/verify-work-auto-transition.test.cjs",
276
315
  "tests/verify.test.cjs",
277
316
  "tests/windsurf-hooks-bridge.test.cjs",
278
317
  "tests/workflow-guard.test.cjs",