@joshuafolkken/kit 1.1471.0 → 1.1784.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 (895) hide show
  1. package/.claude/agents/investigator.md +1 -1
  2. package/.claude/settings.json +6 -6
  3. package/.claude/skills/epic-commands/SKILL.md +26 -77
  4. package/.claude/skills/epic-commands/epic-bundle.md +12 -6
  5. package/.claude/skills/epic-commands/execution-waves.md +1 -2
  6. package/.claude/skills/verify-ui/SKILL.md +1 -2
  7. package/.claude/skills/workflow-commands/SKILL.md +12 -14
  8. package/.claude/skills/workflow-commands/background-commands.md +8 -12
  9. package/.claude/skills/workflow-commands/backlogrun-child.md +13 -18
  10. package/.claude/skills/workflow-commands/backlogrun-handoff-report.md +7 -25
  11. package/.claude/skills/workflow-commands/backlogrun-lanes.md +23 -28
  12. package/.claude/skills/workflow-commands/backlogrun-park.md +16 -31
  13. package/.claude/skills/workflow-commands/backlogrun-progress.md +12 -21
  14. package/.claude/skills/workflow-commands/backlogrun-recovery.md +12 -12
  15. package/.claude/skills/workflow-commands/backlogrun-steps.md +12 -20
  16. package/.claude/skills/workflow-commands/backlogrun.md +32 -51
  17. package/.claude/skills/workflow-commands/chain-rule.md +18 -11
  18. package/.claude/skills/workflow-commands/delegation.md +13 -8
  19. package/.claude/skills/workflow-commands/entry-sequence.md +10 -12
  20. package/.claude/skills/workflow-commands/followup.md +10 -35
  21. package/.claude/skills/workflow-commands/fullrun-steps.md +38 -49
  22. package/.claude/skills/workflow-commands/fullrun.md +6 -8
  23. package/.claude/skills/workflow-commands/halfrun.md +20 -32
  24. package/.claude/skills/workflow-commands/into-target.md +1 -2
  25. package/.claude/skills/workflow-commands/issue-comments.md +19 -15
  26. package/.claude/skills/workflow-commands/issue-scout.md +5 -4
  27. package/.claude/skills/workflow-commands/kickoff.md +24 -23
  28. package/.claude/skills/workflow-commands/latest-gate.md +9 -18
  29. package/.claude/skills/workflow-commands/needs-human-review.md +11 -19
  30. package/.claude/skills/workflow-commands/observation-filing.md +4 -50
  31. package/.claude/skills/workflow-commands/observation-ledger.md +5 -10
  32. package/.claude/skills/workflow-commands/pre-gate-cut.md +22 -44
  33. package/.claude/skills/workflow-commands/prerequisite.md +11 -18
  34. package/.claude/skills/workflow-commands/progress-watcher.md +3 -8
  35. package/.claude/skills/workflow-commands/prrun.md +6 -12
  36. package/.claude/skills/workflow-commands/retrospective.md +5 -5
  37. package/.claude/skills/workflow-commands/split-assessment.md +14 -4
  38. package/.claude/skills/workflow-commands/target-repository.md +1 -2
  39. package/.claude/skills/workflow-commands/working-tree-hold.md +11 -13
  40. package/.codex/hooks.json +6 -6
  41. package/.github/actions/setup-node/action.yml +10 -1
  42. package/.github/actions/setup-pnpm/action.yml +1 -1
  43. package/.github/dependabot.yml +16 -0
  44. package/.github/release.yml +0 -2
  45. package/.github/workflows/ci.yml +121 -11
  46. package/.github/workflows/publish.yml +10 -3
  47. package/.github/workflows/sonar-qube.yml +1 -0
  48. package/.prettierignore +2 -0
  49. package/.vscode/tasks.json +1 -2
  50. package/CLAUDE.md +4 -8
  51. package/README.md +4 -2
  52. package/SECURITY.md +1 -1
  53. package/cspell/index.yaml +7 -0
  54. package/dist/CLAUDE.md +4 -8
  55. package/dist/commands/document-read-cli.js +882 -0
  56. package/dist/commands/{document-section-cli.js → document-section-main.js} +137 -62
  57. package/dist/commands/read-set-cli.js +1867 -0
  58. package/dist/commands/run-prep-main.js +21653 -0
  59. package/dist/commands/run-step-cli.js +23880 -0
  60. package/dist/config-merge/index.js +5 -1
  61. package/dist/hooks/audit-provision.js +20 -35
  62. package/dist/hooks/{chunk-DGT54IH5.js → chunk-AZX4FGQ3.js} +63 -17
  63. package/dist/hooks/chunk-CWMBGKYW.js +6483 -0
  64. package/dist/hooks/chunk-O2YBIDSI.js +4306 -0
  65. package/dist/hooks/{chunk-AS74OU3D.js → chunk-PT5R6UJD.js} +4582 -2118
  66. package/dist/hooks/chunk-TUIFS5E7.js +72 -0
  67. package/dist/hooks/{chunk-723HKZO5.js → chunk-VWWCFGWK.js} +1 -1
  68. package/dist/hooks/{chunk-E7OIKX5Z.js → chunk-WR2KQAYZ.js} +1863 -382
  69. package/dist/hooks/{chunk-KC5AK2GF.js → chunk-XGBNSWEI.js} +248 -46
  70. package/dist/hooks/chunk-YCDOIR3I.js +3456 -0
  71. package/dist/hooks/codex-hook-adapter.js +10 -19
  72. package/dist/hooks/format-edited.js +5 -5
  73. package/dist/hooks/inputs.json +436 -257
  74. package/dist/hooks/pretool-guard.js +7 -22
  75. package/dist/hooks/session-lang.js +380 -42
  76. package/dist/hooks/stop-guard.js +8711 -782
  77. package/dist/josh.js +5263 -997
  78. package/dist/self-sync-guard/index.js +74 -10
  79. package/dist/version/index.js +115 -406
  80. package/eslint/base.js +1 -1
  81. package/lefthook/base.yml +8 -4
  82. package/package.json +17 -53
  83. package/pnpm-workspace.yaml +4 -2
  84. package/prompts/coding-standards.md +1 -1
  85. package/prompts/collaboration-workflow/file-edits.md +1 -9
  86. package/prompts/collaboration-workflow/gh-rest.md +1 -2
  87. package/prompts/collaboration-workflow/issue-citation.md +2 -4
  88. package/prompts/collaboration-workflow/issue-template.md +42 -17
  89. package/prompts/collaboration-workflow/lane-instructions.md +34 -0
  90. package/prompts/collaboration-workflow/measurement.md +37 -0
  91. package/prompts/collaboration-workflow/operating-rules.md +6 -12
  92. package/prompts/collaboration-workflow/output-bounds.md +4 -9
  93. package/prompts/collaboration-workflow/overview.md +1 -1
  94. package/prompts/collaboration-workflow/plan-comment.md +3 -42
  95. package/prompts/collaboration-workflow/principles.md +19 -8
  96. package/prompts/collaboration-workflow/report-format.md +37 -57
  97. package/prompts/collaboration-workflow/residency.md +12 -8
  98. package/prompts/collaboration-workflow/rule-delivery.md +3 -11
  99. package/prompts/collaboration-workflow/shell-body.md +8 -18
  100. package/prompts/collaboration-workflow/turn-batching.md +4 -6
  101. package/prompts/collaboration-workflow/upstream-interrupt.md +16 -6
  102. package/prompts/collaboration-workflow/wip-cap.md +7 -7
  103. package/prompts/collaboration-workflow.md +4 -7
  104. package/prompts/refactoring.md +1 -1
  105. package/prompts/review-rubric.md +1 -2
  106. package/prompts/review.md +45 -26
  107. package/prompts/testing-guide.md +10 -45
  108. package/scripts/agent/agent-argv.ts +20 -4
  109. package/scripts/agent/agent-event.ts +15 -15
  110. package/scripts/agent/agent-exit-record.ts +13 -1
  111. package/scripts/agent/agent-role-profile.ts +101 -45
  112. package/scripts/agent/agent-safe-text.ts +60 -0
  113. package/scripts/agent/api-auth.ts +41 -0
  114. package/scripts/agent/api-outage.ts +1 -1
  115. package/scripts/agent/claude-agent-argv.ts +14 -0
  116. package/scripts/agent/codex-agent-argv.ts +2 -0
  117. package/scripts/agent/lane-instructions.ts +144 -0
  118. package/scripts/auto-ok/auto-ok-cli.ts +14 -16
  119. package/scripts/auto-ok/auto-ok-judge-read.ts +12 -3
  120. package/scripts/auto-ok/auto-ok-judge-write.ts +46 -19
  121. package/scripts/auto-ok/auto-ok-judge.ts +13 -2
  122. package/scripts/auto-ok/auto-ok-main.ts +17 -0
  123. package/scripts/backlog/backlog-arrival.ts +14 -3
  124. package/scripts/backlog/backlog-budget-cli.ts +7 -33
  125. package/scripts/backlog/backlog-budget-main.ts +16 -0
  126. package/scripts/backlog/backlog-budget.ts +6 -7
  127. package/scripts/backlog/backlog-defect-priority.ts +4 -3
  128. package/scripts/backlog/backlog-drive-adopt.ts +67 -0
  129. package/scripts/backlog/backlog-drive-args.ts +4 -5
  130. package/scripts/backlog/backlog-drive-cli.ts +113 -28
  131. package/scripts/backlog/backlog-drive-hold.ts +162 -0
  132. package/scripts/backlog/backlog-drive-idle.ts +151 -0
  133. package/scripts/backlog/backlog-drive-judge.ts +25 -0
  134. package/scripts/backlog/backlog-drive-memory.ts +126 -0
  135. package/scripts/backlog/backlog-drive-named-offer.ts +5 -10
  136. package/scripts/backlog/backlog-drive-named.ts +54 -7
  137. package/scripts/backlog/backlog-drive-offer-argv.ts +3 -8
  138. package/scripts/backlog/backlog-drive-paused.ts +169 -0
  139. package/scripts/backlog/backlog-drive-restore.ts +39 -8
  140. package/scripts/backlog/backlog-drive-seats.ts +18 -8
  141. package/scripts/backlog/backlog-drive-token-handling.ts +38 -0
  142. package/scripts/backlog/backlog-drive.ts +79 -75
  143. package/scripts/backlog/backlog-next-main.ts +16 -0
  144. package/scripts/backlog/backlog-next-shared.ts +73 -0
  145. package/scripts/backlog/backlog-next.ts +48 -16
  146. package/scripts/backlog/backlog-occupied.ts +69 -0
  147. package/scripts/backlog/backlog-offer-cli.ts +6 -21
  148. package/scripts/backlog/backlog-offer-exclude.ts +15 -0
  149. package/scripts/backlog/backlog-offer-main.ts +12 -0
  150. package/scripts/backlog/backlog-offer.ts +36 -3
  151. package/scripts/backlog/backlog-overlap.ts +22 -4
  152. package/scripts/backlog/backlog-plan-read.ts +6 -2
  153. package/scripts/backlog/backlog-plan.ts +18 -4
  154. package/scripts/backlog/backlog-pool.ts +10 -10
  155. package/scripts/backlog/backlog-rank.ts +10 -2
  156. package/scripts/backlog/backlog-ready.ts +137 -18
  157. package/scripts/backlog/backlog-stalled-detect.ts +109 -36
  158. package/scripts/backlog/backlog-stalled.ts +52 -16
  159. package/scripts/backlog/backlog-wait-cause.ts +86 -0
  160. package/scripts/backlog/backlog-waves.ts +39 -13
  161. package/scripts/backlog/backlogrun-args.ts +19 -7
  162. package/scripts/backlog/backlogrun-cli.ts +19 -5
  163. package/scripts/backlog/backlogrun-launch.ts +6 -0
  164. package/scripts/backlog/backlogrun-restart.ts +97 -0
  165. package/scripts/backlog/backlogrun-stop.ts +79 -7
  166. package/scripts/behavior/behavior-cli.ts +2 -2
  167. package/scripts/behavior/behavior-rules.ts +47 -24
  168. package/scripts/build/build-bin.ts +2 -16
  169. package/scripts/build/build-claude-md.ts +0 -7
  170. package/scripts/build/build-commands.ts +0 -13
  171. package/scripts/build/build-hooks.ts +49 -48
  172. package/scripts/build/hook-bundle-stamp.ts +29 -11
  173. package/scripts/build/local-bin.ts +1 -1
  174. package/scripts/cases/cases-cli.ts +25 -13
  175. package/scripts/cases/cases-interaction-scan.ts +134 -0
  176. package/scripts/cases/cases-interaction.ts +183 -0
  177. package/scripts/cases/cases-logic.ts +39 -6
  178. package/scripts/ci/pr-classification-main.ts +18 -0
  179. package/scripts/ci/pr-classification.ts +10 -17
  180. package/scripts/clone/clone-scan.ts +1 -1
  181. package/scripts/cost-runtime/cost-blocks.ts +22 -37
  182. package/scripts/cost-runtime/cost-cli.ts +31 -14
  183. package/scripts/cost-runtime/cost-main.ts +12 -0
  184. package/scripts/cost-runtime/cost-transcript.ts +1 -0
  185. package/scripts/delegation/delegation-policy.ts +17 -4
  186. package/scripts/delegation/duplicate-read-guard.ts +2 -10
  187. package/scripts/delegation/investigation-guard.ts +15 -73
  188. package/scripts/delegation/investigation-reads.ts +3 -5
  189. package/scripts/dependabot/dependabot-cooldown.ts +194 -0
  190. package/scripts/discovery/repo-discovery.ts +24 -6
  191. package/scripts/doctor/doctor-consumer.ts +2 -5
  192. package/scripts/document/document-byte-budget.ts +9 -6
  193. package/scripts/document/document-scan.ts +1 -1
  194. package/scripts/document/document-section-cli.ts +17 -13
  195. package/scripts/document/document-section-main.ts +12 -0
  196. package/scripts/document/entry-read-budget.ts +2 -2
  197. package/scripts/document/read-set-cli.ts +4 -1
  198. package/scripts/epic/epic-audit-cli.ts +12 -6
  199. package/scripts/epic/epic-audit-orphans.ts +5 -8
  200. package/scripts/epic/epic-audit.ts +52 -1
  201. package/scripts/epic/epic-bundle-apply.ts +137 -0
  202. package/scripts/epic/epic-bundle-cli.ts +32 -121
  203. package/scripts/epic/epic-bundle-evidence.ts +49 -26
  204. package/scripts/epic/epic-bundle-format.ts +116 -0
  205. package/scripts/epic/epic-bundle-main.ts +17 -0
  206. package/scripts/epic/epic-bundle-referenced.ts +14 -3
  207. package/scripts/epic/epic-bundle.ts +17 -9
  208. package/scripts/epic/epic-busy.ts +5 -12
  209. package/scripts/epic/epic-classify.ts +24 -15
  210. package/scripts/epic/epic-cli-argv.ts +31 -0
  211. package/scripts/epic/epic-cli-decide.ts +42 -0
  212. package/scripts/epic/epic-cli.ts +6 -38
  213. package/scripts/epic/epic-close.ts +112 -55
  214. package/scripts/epic/epic-cross-repo.ts +4 -7
  215. package/scripts/epic/epic-decide.ts +119 -0
  216. package/scripts/epic/epic-decision.ts +9 -0
  217. package/scripts/epic/epic-fetch.ts +4 -0
  218. package/scripts/epic/epic-graph.ts +2 -0
  219. package/scripts/epic/epic-issue.ts +5 -1
  220. package/scripts/epic/epic-label-age.ts +1 -1
  221. package/scripts/epic/epic-lane-offer.ts +39 -4
  222. package/scripts/epic/epic-next-main.ts +24 -0
  223. package/scripts/epic/epic-next.ts +6 -24
  224. package/scripts/epic/epic-outside-blocker.ts +6 -2
  225. package/scripts/epic/epic-parse.ts +9 -3
  226. package/scripts/epic/epic-read.ts +1 -0
  227. package/scripts/epic/epic-reconcile.ts +39 -0
  228. package/scripts/epic/epic-run.ts +10 -1
  229. package/scripts/epic/epic-solo.ts +50 -14
  230. package/scripts/epic/epic.ts +41 -7
  231. package/scripts/exports/unused-members-cli.ts +2 -2
  232. package/scripts/followup/followup-checks-event.ts +8 -3
  233. package/scripts/followup/followup-coderabbit-wait.ts +82 -0
  234. package/scripts/followup/followup-review-gates.ts +81 -0
  235. package/scripts/followup/git-followup-stages.ts +13 -3
  236. package/scripts/followup/git-followup-workflow.ts +31 -60
  237. package/scripts/followup/git-pr-followup-wrapup.ts +9 -14
  238. package/scripts/followup/git-pr-followup.ts +36 -8
  239. package/scripts/fresh-machine/fresh-machine-cli.ts +1 -1
  240. package/scripts/fresh-machine/fresh-machine-run.ts +8 -8
  241. package/scripts/fresh-machine/specs/kit-test-backlogrun.json +1 -1
  242. package/scripts/gate/busy-average.ts +58 -0
  243. package/scripts/gate/check-cpu.ts +60 -0
  244. package/scripts/gate/check-inputs.ts +73 -0
  245. package/scripts/gate/check-reuse.ts +141 -0
  246. package/scripts/gate/command-memory.ts +192 -0
  247. package/scripts/gate/core-admission.ts +218 -28
  248. package/scripts/gate/core-budget-timing.ts +37 -0
  249. package/scripts/gate/core-budget.ts +150 -119
  250. package/scripts/gate/core-wait-record.ts +48 -0
  251. package/scripts/gate/core-wait.ts +162 -0
  252. package/scripts/gate/core-weights.ts +86 -0
  253. package/scripts/gate/free-cores.ts +72 -0
  254. package/scripts/gate/gate-ledger.ts +49 -7
  255. package/scripts/gate/gate-plan.ts +44 -15
  256. package/scripts/gate/gate-report.ts +29 -4
  257. package/scripts/gate/gate-run-steps.ts +195 -0
  258. package/scripts/gate/gate-skip.ts +12 -2
  259. package/scripts/gate/gate-steps.ts +12 -1
  260. package/scripts/gate/held-mark.ts +55 -0
  261. package/scripts/gate/input-fingerprint.ts +42 -0
  262. package/scripts/gate/machine-capacity.ts +124 -31
  263. package/scripts/gate/moved-paths.ts +67 -0
  264. package/scripts/gate/pre-commit-type-check.ts +14 -1
  265. package/scripts/gate/project-checks.ts +5 -12
  266. package/scripts/gate/scoped-green.ts +12 -8
  267. package/scripts/gate/since-green.ts +62 -0
  268. package/scripts/gate/toolchain-inputs.ts +115 -0
  269. package/scripts/gate/verification-gate.ts +65 -129
  270. package/scripts/gate/verification-inputs.ts +250 -0
  271. package/scripts/gh/gh-author-association.ts +96 -9
  272. package/scripts/gh/git-ai-review-scan.ts +4 -2
  273. package/scripts/gh/git-gh-api-path.ts +15 -0
  274. package/scripts/gh/git-gh-branch-rules.ts +73 -0
  275. package/scripts/gh/git-gh-conditional.ts +5 -2
  276. package/scripts/gh/git-gh-issue-read.ts +5 -1
  277. package/scripts/gh/git-gh-issue-rest.ts +1 -0
  278. package/scripts/gh/git-gh-issue-write.ts +77 -17
  279. package/scripts/gh/git-gh-issue.ts +7 -3
  280. package/scripts/gh/git-gh-poll-read.ts +89 -0
  281. package/scripts/gh/git-gh-pr-auto-merge.ts +8 -3
  282. package/scripts/gh/git-gh-pr-rest.ts +1 -1
  283. package/scripts/gh/git-gh-pr-snapshot.ts +33 -20
  284. package/scripts/gh/git-gh-pr.ts +27 -15
  285. package/scripts/gh/git-pr-checks-eval.ts +39 -7
  286. package/scripts/gh/git-pr-checks-parse.ts +39 -9
  287. package/scripts/gh/git-pr-merge-checked.ts +80 -0
  288. package/scripts/gh/git-pr.ts +13 -1
  289. package/scripts/git/base-tree.ts +19 -2
  290. package/scripts/git/changed-file-scope.ts +6 -4
  291. package/scripts/git/changed-paths.ts +18 -1
  292. package/scripts/git/git-diff-reads.ts +27 -2
  293. package/scripts/git/git-grep-hits.ts +85 -0
  294. package/scripts/git/git-location-environment.ts +1 -1
  295. package/scripts/git/git-merge-conflicts.ts +83 -0
  296. package/scripts/git/git-preflight.ts +37 -12
  297. package/scripts/git/git-push-transport.ts +1 -2
  298. package/scripts/git/git-schemas.ts +17 -7
  299. package/scripts/git/git-spawn.ts +1 -2
  300. package/scripts/git/git-status.ts +4 -4
  301. package/scripts/git/main-merge-main.ts +12 -0
  302. package/scripts/git/main-merge-regenerate.ts +78 -0
  303. package/scripts/git/main-merge.ts +39 -14
  304. package/scripts/git/main-sync-main.ts +12 -0
  305. package/scripts/git/main-sync.ts +0 -9
  306. package/scripts/git/stash/git-stash.ts +27 -4
  307. package/scripts/git/stash/{stash-pop-args.ts → stash-args.ts} +13 -10
  308. package/scripts/git/stash/stash-pop-cli.ts +6 -12
  309. package/scripts/git/stash/stash-pop-main.ts +12 -0
  310. package/scripts/git/stash/stash-push-cli.ts +76 -0
  311. package/scripts/git/stash/stash-push-main.ts +12 -0
  312. package/scripts/hooks/batch-guard.ts +5 -16
  313. package/scripts/hooks/check-commit-message-main.ts +8 -0
  314. package/scripts/hooks/check-commit-message.ts +4 -7
  315. package/scripts/hooks/format-edited-file.ts +8 -24
  316. package/scripts/hooks/pre-commit-lint.ts +118 -0
  317. package/scripts/hooks/pre-push-unit.ts +4 -2
  318. package/scripts/hooks/pretool-guard-cli.ts +1 -8
  319. package/scripts/hooks/pretool-guard.ts +57 -69
  320. package/scripts/hooks/reserved-run.ts +67 -8
  321. package/scripts/hooks/run-hook.sh +18 -11
  322. package/scripts/hooks/shell-rules-notice.ts +37 -0
  323. package/scripts/hooks/stop-actions.ts +185 -0
  324. package/scripts/hooks/stop-guard.ts +72 -27
  325. package/scripts/init/hook-command-rewrite.ts +19 -5
  326. package/scripts/init/hook-launch.ts +15 -12
  327. package/scripts/init/init-actions.ts +0 -6
  328. package/scripts/init/init-ai-copy.ts +10 -36
  329. package/scripts/init/init-bootstrap.ts +9 -8
  330. package/scripts/init/init-dry-run-report.ts +1 -1
  331. package/scripts/init/init-dry-run.ts +1 -1
  332. package/scripts/init/init-file-action.ts +7 -9
  333. package/scripts/init/init-logic-json-merge.ts +2 -2
  334. package/scripts/init/init-logic-migrate.ts +9 -82
  335. package/scripts/init/init-logic.ts +3 -2
  336. package/scripts/init/init-main.ts +12 -0
  337. package/scripts/init/init.ts +5 -12
  338. package/scripts/init/kit-development-versions.ts +3 -7
  339. package/scripts/init/kit-written-paths.ts +2 -2
  340. package/scripts/init/project-profile.ts +5 -4
  341. package/scripts/init/tsconfig-preset-migration.ts +2 -1
  342. package/scripts/init/vscode-tasks.ts +1 -1
  343. package/scripts/issue/defect-origin-cli.ts +106 -0
  344. package/scripts/issue/defect-origin-line.ts +60 -0
  345. package/scripts/issue/defect-origin-main.ts +11 -0
  346. package/scripts/issue/defect-origin.ts +114 -0
  347. package/scripts/issue/defect-rate-cli.ts +34 -78
  348. package/scripts/issue/defect-rate.ts +0 -16
  349. package/scripts/issue/defect-report-cli.ts +128 -0
  350. package/scripts/issue/defect-report-format.ts +56 -0
  351. package/scripts/issue/defect-report-main.ts +11 -0
  352. package/scripts/issue/defect-report.ts +160 -0
  353. package/scripts/issue/expected-effect-lint.ts +60 -0
  354. package/scripts/issue/issue-already-done-cli.ts +62 -0
  355. package/scripts/issue/issue-body-or-comment.ts +40 -0
  356. package/scripts/issue/issue-cite-cli.ts +33 -22
  357. package/scripts/issue/issue-cite-main.ts +12 -0
  358. package/scripts/issue/issue-classification.ts +13 -8
  359. package/scripts/issue/issue-comment-cli.ts +10 -24
  360. package/scripts/issue/issue-comment-main.ts +12 -0
  361. package/scripts/issue/issue-evidence-exit.ts +100 -0
  362. package/scripts/issue/issue-file-cli.ts +29 -7
  363. package/scripts/issue/issue-file.ts +19 -19
  364. package/scripts/issue/issue-fold-cli.ts +2 -11
  365. package/scripts/issue/issue-fold-main.ts +12 -0
  366. package/scripts/issue/issue-labels.ts +81 -90
  367. package/scripts/issue/issue-lint-cli.ts +7 -13
  368. package/scripts/issue/issue-lint-main.ts +12 -0
  369. package/scripts/issue/issue-measured-cli.ts +56 -0
  370. package/scripts/issue/issue-merged.ts +19 -2
  371. package/scripts/issue/issue-not-before-label.ts +135 -0
  372. package/scripts/issue/issue-not-before.ts +111 -0
  373. package/scripts/issue/issue-number-shape.ts +15 -1
  374. package/scripts/issue/issue-park.ts +28 -0
  375. package/scripts/issue/issue-plan-cli.ts +151 -0
  376. package/scripts/issue/issue-priority.ts +151 -0
  377. package/scripts/issue/issue-rank.ts +7 -1
  378. package/scripts/issue/issue-read-cli.ts +3 -10
  379. package/scripts/issue/issue-read-main.ts +12 -0
  380. package/scripts/issue/issue-read.ts +29 -5
  381. package/scripts/issue/issue-release-cli.ts +0 -10
  382. package/scripts/issue/issue-release-main.ts +13 -0
  383. package/scripts/issue/issue-release.ts +7 -12
  384. package/scripts/issue/issue-sample-gate.ts +192 -0
  385. package/scripts/issue/issue-sample-source.ts +76 -0
  386. package/scripts/issue/issue-scout-cli.ts +19 -25
  387. package/scripts/issue/issue-scout-main.ts +14 -0
  388. package/scripts/issue/issue-state-cli.ts +0 -10
  389. package/scripts/issue/issue-state-main.ts +12 -0
  390. package/scripts/issue/issue-watch-diff.ts +56 -15
  391. package/scripts/issue/issue-watch.ts +2 -1
  392. package/scripts/issue/issue-wip.ts +2 -7
  393. package/scripts/issue/markdown-section.ts +19 -5
  394. package/scripts/issue/measure-rerun-cli.ts +13 -8
  395. package/scripts/issue/plan-consumers-cli.ts +39 -0
  396. package/scripts/issue/plan-consumers-main.ts +11 -0
  397. package/scripts/issue/plan-consumers-section.ts +55 -0
  398. package/scripts/issue/plan-consumers.ts +127 -0
  399. package/scripts/josh/agent-session-environment.ts +1 -1
  400. package/scripts/josh/command-usage.ts +82 -0
  401. package/scripts/josh/file-map-stamp.ts +49 -16
  402. package/scripts/josh/hook-decision.ts +32 -20
  403. package/scripts/josh/josh-command-map.ts +6 -1
  404. package/scripts/josh/josh-command-types.ts +65 -13
  405. package/scripts/josh/josh-commands-agent-hooks.ts +83 -0
  406. package/scripts/josh/josh-commands-ai.ts +169 -157
  407. package/scripts/josh/josh-commands-backlog.ts +82 -16
  408. package/scripts/josh/josh-commands-clone.ts +1 -0
  409. package/scripts/josh/josh-commands-development.ts +111 -71
  410. package/scripts/josh/josh-commands-document.ts +43 -1
  411. package/scripts/josh/josh-commands-epic.ts +171 -0
  412. package/scripts/josh/josh-commands-hooks.ts +31 -2
  413. package/scripts/josh/josh-commands-issue-write.ts +181 -0
  414. package/scripts/josh/josh-commands-issue.ts +124 -24
  415. package/scripts/josh/josh-commands-lane.ts +112 -2
  416. package/scripts/josh/josh-commands-lint.ts +19 -8
  417. package/scripts/josh/josh-commands-maintenance.ts +112 -4
  418. package/scripts/josh/josh-commands-pause.ts +29 -0
  419. package/scripts/josh/josh-commands-progress.ts +87 -0
  420. package/scripts/josh/josh-commands-project.ts +138 -9
  421. package/scripts/josh/josh-commands-review.ts +124 -0
  422. package/scripts/josh/josh-commands-run.ts +211 -23
  423. package/scripts/josh/josh-commands-ship.ts +169 -0
  424. package/scripts/josh/josh-commands-split.ts +9 -0
  425. package/scripts/josh/josh-commands-versioning.ts +49 -2
  426. package/scripts/josh/josh-commands-workflow.ts +149 -6
  427. package/scripts/josh/josh-logic.ts +11 -27
  428. package/scripts/josh/josh.ts +14 -5
  429. package/scripts/josh/package-directory.ts +18 -0
  430. package/scripts/josh/process-identity.ts +13 -4
  431. package/scripts/josh/session-language-cli.ts +4 -8
  432. package/scripts/josh/session-language-main.ts +13 -0
  433. package/scripts/josh/session-language.ts +6 -1
  434. package/scripts/josh/shared-cache.ts +90 -0
  435. package/scripts/josh/stamp-file.ts +9 -15
  436. package/scripts/lane/lane-await.ts +51 -12
  437. package/scripts/lane/lane-cache.ts +5 -30
  438. package/scripts/lane/lane-capacity.ts +19 -22
  439. package/scripts/lane/lane-check-stats.ts +97 -0
  440. package/scripts/lane/lane-child-invocation.ts +43 -4
  441. package/scripts/lane/lane-cli.ts +15 -5
  442. package/scripts/lane/lane-close.ts +86 -18
  443. package/scripts/lane/lane-core-wait-stats.ts +66 -0
  444. package/scripts/lane/lane-dispatch.ts +27 -6
  445. package/scripts/lane/lane-gap-stats.ts +156 -0
  446. package/scripts/lane/lane-guard-policy.ts +2 -2
  447. package/scripts/lane/lane-handoff.ts +76 -1
  448. package/scripts/lane/lane-held-stats.ts +129 -0
  449. package/scripts/lane/lane-install.ts +16 -15
  450. package/scripts/lane/lane-launch-cli.ts +0 -9
  451. package/scripts/lane/lane-launch-main.ts +12 -0
  452. package/scripts/lane/lane-ledger-schema.ts +266 -0
  453. package/scripts/lane/lane-ledger.ts +108 -97
  454. package/scripts/lane/lane-limit-cli.ts +19 -9
  455. package/scripts/lane/lane-measure-cli.ts +58 -10
  456. package/scripts/lane/lane-open.ts +9 -1
  457. package/scripts/lane/lane-parked.ts +3 -3
  458. package/scripts/lane/lane-pause-cli.ts +130 -0
  459. package/scripts/lane/lane-pause.ts +158 -0
  460. package/scripts/lane/lane-preserve.ts +29 -1
  461. package/scripts/lane/lane-process-table.ts +166 -0
  462. package/scripts/lane/lane-reap-settle.ts +124 -0
  463. package/scripts/lane/lane-reap.ts +50 -15
  464. package/scripts/lane/lane-registry.ts +33 -10
  465. package/scripts/lane/lane-residents.ts +162 -0
  466. package/scripts/lane/lane-restart.ts +26 -27
  467. package/scripts/lane/lane-round-two-stats.ts +49 -0
  468. package/scripts/lane/lane-sampler.ts +4 -0
  469. package/scripts/lane/lane-session-action.ts +160 -0
  470. package/scripts/lane/lane-session-broker.ts +134 -134
  471. package/scripts/lane/lane-snapshot-trace.ts +84 -0
  472. package/scripts/lane/lane-spans.ts +51 -0
  473. package/scripts/lane/lane-spent.ts +6 -3
  474. package/scripts/lane/lane-stage-stats.ts +7 -2
  475. package/scripts/lane/lane-state.ts +302 -0
  476. package/scripts/lane/lane-stats.ts +58 -4
  477. package/scripts/lane/lane-stop-stats.ts +113 -37
  478. package/scripts/lane/lane-test-related-stats.ts +127 -0
  479. package/scripts/lane/lane-transcript-calls.ts +145 -0
  480. package/scripts/lane/lane-transcript-stats.ts +168 -0
  481. package/scripts/lane/lane-vacant.ts +13 -3
  482. package/scripts/lane/lane-withdraw-cli.ts +72 -0
  483. package/scripts/lane/lane-withdraw.ts +183 -0
  484. package/scripts/lane/process-directories.ts +70 -0
  485. package/scripts/lane/process-lane-marks.ts +94 -0
  486. package/scripts/lib/atomic-write.ts +62 -0
  487. package/scripts/lib/buffered-process.ts +12 -5
  488. package/scripts/lib/cli-flags.ts +53 -0
  489. package/scripts/lib/figure-format.ts +63 -0
  490. package/scripts/lib/json-value.ts +9 -1
  491. package/scripts/lib/package-manifest.ts +35 -0
  492. package/scripts/lib/read-file.ts +3 -1
  493. package/scripts/lib/stamped-memo.ts +63 -0
  494. package/scripts/lib/stdout-on-stderr.ts +24 -0
  495. package/scripts/lib/timeouts.ts +9 -0
  496. package/scripts/lib/transcript-record.ts +91 -0
  497. package/scripts/lines/effective-limit.ts +1 -1
  498. package/scripts/lint/eslint-cache-dependencies.ts +145 -0
  499. package/scripts/lint/eslint-daemon.ts +265 -0
  500. package/scripts/lint/format.ts +14 -5
  501. package/scripts/lint/import-graph.ts +279 -0
  502. package/scripts/lint/lint-gate-scope.ts +102 -0
  503. package/scripts/lint/lint-parallel-main.ts +19 -0
  504. package/scripts/lint/lint-parallel.ts +72 -33
  505. package/scripts/lint/lint-related-scope.ts +33 -24
  506. package/scripts/lint/lint-related.ts +38 -6
  507. package/scripts/notify/confirmation-options.ts +1 -2
  508. package/scripts/notify/telegram-notify.ts +20 -20
  509. package/scripts/notify/telegram-test-logic.ts +0 -1
  510. package/scripts/notify/telegram-test-main.ts +8 -0
  511. package/scripts/notify/telegram-test.ts +12 -11
  512. package/scripts/observations/observation-ledger.ts +13 -0
  513. package/scripts/observations/observations-flush-landing.ts +5 -3
  514. package/scripts/observations/observations-flush.ts +6 -1
  515. package/scripts/overrides/overrides-check.ts +2 -5
  516. package/scripts/overrides/overrides-files.ts +2 -1
  517. package/scripts/overrides/overrides-logic.ts +3 -6
  518. package/scripts/package/verify-optional-eslint-install.ts +8 -6
  519. package/scripts/propagate/propagate-publish.ts +2 -7
  520. package/scripts/propagate/propagate-targets.ts +4 -12
  521. package/scripts/refactor/import-graph.ts +9 -7
  522. package/scripts/release/github-release-runs.ts +17 -6
  523. package/scripts/release/release-approval-prune.ts +18 -0
  524. package/scripts/release/release-history.ts +1 -3
  525. package/scripts/release/release-progress.ts +42 -22
  526. package/scripts/release/release-publish-run.ts +39 -0
  527. package/scripts/release/release-publish.ts +6 -6
  528. package/scripts/release/release-scope-cli.ts +0 -10
  529. package/scripts/release/release-scope-main.ts +12 -0
  530. package/scripts/repo/repo-setting.ts +3 -6
  531. package/scripts/repo/required-checks-logic.ts +6 -15
  532. package/scripts/report/report-format-reference.ts +4 -0
  533. package/scripts/report/report-labels.ts +155 -0
  534. package/scripts/report/report-lint-cli.ts +3 -0
  535. package/scripts/report/report-lint.ts +85 -110
  536. package/scripts/report/report-template-cli.ts +59 -0
  537. package/scripts/report/report-template.ts +112 -0
  538. package/scripts/review/acceptance-map-check.ts +61 -0
  539. package/scripts/review/acceptance-map.ts +206 -0
  540. package/scripts/review/removed-tests-check.ts +86 -0
  541. package/scripts/review/removed-tests.ts +149 -0
  542. package/scripts/review/review-brief-cli.ts +82 -16
  543. package/scripts/review/review-brief-main.ts +12 -0
  544. package/scripts/review/review-brief.ts +31 -3
  545. package/scripts/review/review-code-tree.ts +10 -6
  546. package/scripts/review/review-comment-round.ts +26 -8
  547. package/scripts/review/review-finding-ledger.ts +30 -15
  548. package/scripts/review/review-interaction.ts +94 -0
  549. package/scripts/review/review-readers-scan.ts +163 -0
  550. package/scripts/review/review-record-cli.ts +69 -30
  551. package/scripts/review/review-record-main.ts +12 -0
  552. package/scripts/review/review-round-one-blobs.ts +221 -0
  553. package/scripts/review/review-round2-cli.ts +49 -12
  554. package/scripts/review/review-round2.ts +80 -12
  555. package/scripts/review/review-stamps.ts +19 -1
  556. package/scripts/review/review-stop-log.ts +96 -0
  557. package/scripts/review/review-stops-cli.ts +85 -0
  558. package/scripts/review/review-tree.ts +6 -17
  559. package/scripts/review/review-untouched-readers.ts +146 -0
  560. package/scripts/review/test-titles.ts +118 -0
  561. package/scripts/rules/agent-model.ts +67 -0
  562. package/scripts/rules/bash-triggers.ts +46 -3
  563. package/scripts/rules/decision-oracle-batch.ts +9 -1
  564. package/scripts/rules/decision-oracle.ts +2 -2
  565. package/scripts/rules/delivered-rules.ts +90 -3
  566. package/scripts/rules/destructive-command.ts +8 -1
  567. package/scripts/rules/direct-filing.ts +10 -2
  568. package/scripts/rules/direct-issue-comment.ts +117 -0
  569. package/scripts/rules/direct-pr-create.ts +69 -3
  570. package/scripts/rules/early-heartbeat.ts +2 -1
  571. package/scripts/rules/file-body.ts +7 -0
  572. package/scripts/rules/filing-cap.ts +8 -0
  573. package/scripts/rules/firing-point.ts +6 -5
  574. package/scripts/rules/git-argv.ts +72 -14
  575. package/scripts/rules/git-force.ts +12 -2
  576. package/scripts/rules/guard-remedy.ts +121 -0
  577. package/scripts/rules/implementation-cut-verdict.ts +1 -1
  578. package/scripts/rules/implementation-cut.ts +11 -3
  579. package/scripts/rules/index-guard.ts +8 -1
  580. package/scripts/rules/issue-comments.ts +76 -7
  581. package/scripts/rules/josh-git-bare.ts +7 -0
  582. package/scripts/rules/lane-background.ts +67 -25
  583. package/scripts/rules/lane-carry-conflict.ts +6 -0
  584. package/scripts/rules/lane-direct-tool.ts +74 -0
  585. package/scripts/rules/lane-interactive-ask.ts +9 -2
  586. package/scripts/rules/lane-park.ts +45 -23
  587. package/scripts/rules/lane-split-park.ts +10 -2
  588. package/scripts/rules/lane-switch-main.ts +7 -0
  589. package/scripts/rules/last-prompt.ts +50 -5
  590. package/scripts/rules/oracle-consulted.ts +10 -0
  591. package/scripts/rules/oracle-firing.ts +1 -0
  592. package/scripts/rules/oracle-list-cli.ts +7 -0
  593. package/scripts/rules/permission-guards.ts +3 -0
  594. package/scripts/rules/piped-verification.ts +4 -2
  595. package/scripts/rules/poll-loop.ts +7 -0
  596. package/scripts/rules/pr-merge.ts +123 -0
  597. package/scripts/rules/protected-files.ts +32 -5
  598. package/scripts/rules/raw-field-body.ts +6 -0
  599. package/scripts/rules/rule-body-guard.ts +8 -0
  600. package/scripts/rules/rule-list.ts +12 -28
  601. package/scripts/rules/rule-rewrite.ts +114 -0
  602. package/scripts/rules/rule-value-cache.ts +4 -9
  603. package/scripts/rules/rule-value-cli.ts +51 -32
  604. package/scripts/rules/rule-value.ts +8 -2
  605. package/scripts/rules/shell-segments.ts +50 -0
  606. package/scripts/rules/stop-decision.ts +77 -0
  607. package/scripts/rules/stop-rule-rows.ts +64 -0
  608. package/scripts/rules/stop-rules.ts +150 -51
  609. package/scripts/rules/tail-commands.ts +15 -1
  610. package/scripts/rules/test-declared-commit.ts +11 -1
  611. package/scripts/rules/third-party-write.ts +7 -0
  612. package/scripts/rules/timed-rerun.ts +69 -0
  613. package/scripts/rules/worktree-guard.ts +13 -3
  614. package/scripts/run/board/run-board-app-name.ts +23 -0
  615. package/scripts/run/board/run-board-cli.ts +65 -30
  616. package/scripts/run/board/run-board-closed.ts +8 -2
  617. package/scripts/run/board/run-board-earlier.ts +94 -0
  618. package/scripts/run/board/run-board-ending-reason.ts +67 -0
  619. package/scripts/run/board/run-board-estimate-schedule.ts +103 -0
  620. package/scripts/run/board/run-board-estimate.ts +98 -0
  621. package/scripts/run/board/run-board-fit.ts +153 -36
  622. package/scripts/run/board/run-board-fold.ts +123 -0
  623. package/scripts/run/board/run-board-fresh.ts +2 -2
  624. package/scripts/run/board/run-board-gather-live.ts +29 -0
  625. package/scripts/run/board/run-board-gather-thread.ts +189 -0
  626. package/scripts/run/board/run-board-gather-worker.ts +29 -0
  627. package/scripts/run/board/run-board-gather.ts +187 -0
  628. package/scripts/run/board/run-board-github.ts +119 -31
  629. package/scripts/run/board/run-board-header.ts +86 -21
  630. package/scripts/run/board/run-board-keys.ts +58 -0
  631. package/scripts/run/board/run-board-kind.ts +20 -6
  632. package/scripts/run/board/run-board-labels.ts +118 -71
  633. package/scripts/run/board/run-board-lane-state.ts +109 -0
  634. package/scripts/run/board/run-board-lane-time.ts +122 -0
  635. package/scripts/run/board/run-board-layout.ts +240 -61
  636. package/scripts/run/board/run-board-length.ts +52 -0
  637. package/scripts/run/board/run-board-machine.ts +8 -4
  638. package/scripts/run/board/run-board-main.ts +12 -0
  639. package/scripts/run/board/run-board-notes.ts +52 -31
  640. package/scripts/run/board/run-board-now.ts +1 -1
  641. package/scripts/run/board/run-board-operation.ts +15 -33
  642. package/scripts/run/board/run-board-phase.ts +1 -1
  643. package/scripts/run/board/run-board-plan-shared.ts +115 -0
  644. package/scripts/run/board/run-board-plan.ts +55 -3
  645. package/scripts/run/board/run-board-planning.ts +45 -0
  646. package/scripts/run/board/run-board-priority.ts +44 -0
  647. package/scripts/run/board/run-board-process-groups.ts +195 -0
  648. package/scripts/run/board/run-board-read.ts +153 -13
  649. package/scripts/run/board/run-board-reason.ts +238 -45
  650. package/scripts/run/board/run-board-released.ts +35 -0
  651. package/scripts/run/board/run-board-render-checks.ts +39 -5
  652. package/scripts/run/board/run-board-render-condition.ts +96 -0
  653. package/scripts/run/board/run-board-render-drawn.ts +67 -0
  654. package/scripts/run/board/run-board-render-foot.ts +59 -0
  655. package/scripts/run/board/run-board-render-icon.ts +35 -0
  656. package/scripts/run/board/run-board-render-lanes.ts +145 -0
  657. package/scripts/run/board/run-board-render-lead.ts +80 -0
  658. package/scripts/run/board/run-board-render-legend.ts +117 -47
  659. package/scripts/run/board/run-board-render-notes.ts +156 -29
  660. package/scripts/run/board/run-board-render-processes.ts +196 -0
  661. package/scripts/run/board/run-board-render-section.ts +119 -0
  662. package/scripts/run/board/run-board-render-slot.ts +3 -36
  663. package/scripts/run/board/run-board-render-tail.ts +115 -48
  664. package/scripts/run/board/run-board-render-time.ts +56 -0
  665. package/scripts/run/board/run-board-render-title.ts +117 -24
  666. package/scripts/run/board/run-board-render-waits.ts +125 -0
  667. package/scripts/run/board/run-board-render.ts +206 -259
  668. package/scripts/run/board/run-board-roots.ts +54 -0
  669. package/scripts/run/board/run-board-row-yield.ts +10 -4
  670. package/scripts/run/board/run-board-setup.ts +1 -12
  671. package/scripts/run/board/run-board-snapshot.ts +111 -0
  672. package/scripts/run/board/run-board-spin.ts +2 -2
  673. package/scripts/run/board/run-board-state.ts +23 -29
  674. package/scripts/run/board/run-board-status.ts +206 -79
  675. package/scripts/run/board/run-board-thanks-read.ts +2 -2
  676. package/scripts/run/board/run-board-tick.ts +123 -104
  677. package/scripts/run/board/run-board-usage-board.ts +78 -0
  678. package/scripts/run/board/run-board-usage-lanes.ts +113 -0
  679. package/scripts/run/board/run-board-usage-listing.ts +93 -0
  680. package/scripts/run/board/run-board-usage-read.ts +120 -150
  681. package/scripts/run/board/run-board-usage-rusage.ts +19 -7
  682. package/scripts/run/board/run-board-usage-text.ts +139 -51
  683. package/scripts/run/board/run-board-usage-top.ts +102 -0
  684. package/scripts/run/board/run-board-usage.ts +89 -72
  685. package/scripts/run/board/run-board-usual.ts +20 -9
  686. package/scripts/run/carry/run-carry-args.ts +4 -7
  687. package/scripts/run/carry/run-carry-conversation.ts +1 -1
  688. package/scripts/run/carry/run-carry.ts +9 -4
  689. package/scripts/run/cut/run-cut-cli.ts +3 -2
  690. package/scripts/run/cut/run-cut-handoff.ts +2 -2
  691. package/scripts/run/cut/run-cut-report.ts +16 -0
  692. package/scripts/run/detached-launch.ts +23 -4
  693. package/scripts/run/entry/run-entry-cli.ts +8 -1
  694. package/scripts/run/event/run-event-cli.ts +1 -5
  695. package/scripts/run/event/run-event-filed.ts +12 -6
  696. package/scripts/run/event/run-event-follow.ts +2 -3
  697. package/scripts/run/event/run-event-render.ts +7 -10
  698. package/scripts/run/event/run-event-scope.ts +20 -2
  699. package/scripts/run/event/run-event-stream-emit.ts +78 -11
  700. package/scripts/run/event/run-event-stream.ts +37 -7
  701. package/scripts/run/hold/run-hold-adopt.ts +65 -0
  702. package/scripts/run/hold/run-hold-cli.ts +93 -22
  703. package/scripts/run/hold/run-hold-main.ts +12 -0
  704. package/scripts/run/hold/run-hold-member.ts +37 -0
  705. package/scripts/run/hold/run-hold-session.ts +46 -0
  706. package/scripts/run/hold/run-hold.ts +7 -1
  707. package/scripts/run/hold/run-stop-notify.ts +183 -0
  708. package/scripts/run/launch-priority.ts +32 -0
  709. package/scripts/run/merge/run-merge-auth.ts +31 -0
  710. package/scripts/run/merge/run-merge-cli.ts +72 -107
  711. package/scripts/run/merge/run-merge-close.ts +74 -0
  712. package/scripts/run/merge/run-merge-collect.ts +6 -13
  713. package/scripts/run/merge/run-merge-driver.ts +71 -0
  714. package/scripts/run/merge/run-merge-main.ts +12 -0
  715. package/scripts/run/merge/run-merge-outcome.ts +23 -0
  716. package/scripts/run/merge/run-merge-restart.ts +39 -0
  717. package/scripts/run/merge/run-merge-ship.ts +20 -4
  718. package/scripts/run/merge/run-merge-signals.ts +123 -0
  719. package/scripts/run/merge/run-merge-steps.ts +128 -83
  720. package/scripts/run/merge/run-merge.ts +53 -40
  721. package/scripts/run/park/run-park-cli.ts +91 -0
  722. package/scripts/run/park/run-park.ts +88 -0
  723. package/scripts/run/park/run-stalled.ts +68 -0
  724. package/scripts/run/pause/run-pause-cli.ts +73 -0
  725. package/scripts/run/pause/run-pause.ts +251 -0
  726. package/scripts/run/progress/run-progress-cli.ts +4 -12
  727. package/scripts/run/progress/run-progress-clock.ts +1 -1
  728. package/scripts/run/progress/run-progress-config.ts +6 -14
  729. package/scripts/run/progress/run-progress-main.ts +12 -0
  730. package/scripts/run/progress/run-progress.ts +1 -4
  731. package/scripts/run/review/run-review.ts +2 -1
  732. package/scripts/run/run-ending.ts +1 -0
  733. package/scripts/run/run-invocation.ts +5 -6
  734. package/scripts/run/run-liveness-cli.ts +6 -8
  735. package/scripts/run/run-liveness.ts +61 -30
  736. package/scripts/run/run-next.ts +1 -1
  737. package/scripts/run/run-parent-cut-hook.ts +2 -2
  738. package/scripts/run/run-poll-hook.ts +157 -0
  739. package/scripts/run/run-preflight.ts +18 -3
  740. package/scripts/run/run-prep-cli.ts +1 -10
  741. package/scripts/run/run-prep-locate.ts +7 -50
  742. package/scripts/run/run-prep-main.ts +12 -0
  743. package/scripts/run/run-prep.ts +6 -0
  744. package/scripts/run/run-report-cli.ts +101 -13
  745. package/scripts/run/run-report-handoff.ts +114 -0
  746. package/scripts/run/run-step-cli.ts +22 -15
  747. package/scripts/run/run-step-section.ts +85 -0
  748. package/scripts/run/run-step.ts +1 -1
  749. package/scripts/run/run-stranded-detect.ts +13 -0
  750. package/scripts/run/run-watcher-guard-cli.ts +1 -1
  751. package/scripts/run/run-watcher-guard.ts +1 -1
  752. package/scripts/run/ship/run-ship-args.ts +121 -0
  753. package/scripts/run/ship/run-ship-body-draft.ts +110 -0
  754. package/scripts/run/ship/run-ship-cli.ts +67 -151
  755. package/scripts/run/ship/run-ship-detach.ts +27 -7
  756. package/scripts/run/ship/run-ship-infra-retry.ts +59 -0
  757. package/scripts/run/ship/run-ship-next.ts +27 -3
  758. package/scripts/run/ship/run-ship-overlap.ts +232 -0
  759. package/scripts/run/ship/run-ship-place.ts +96 -0
  760. package/scripts/run/ship/run-ship-pre-detach-timed.ts +43 -0
  761. package/scripts/run/ship/run-ship-pre-detach.ts +102 -27
  762. package/scripts/run/ship/run-ship-preflight.ts +161 -30
  763. package/scripts/run/ship/run-ship-probe.ts +11 -3
  764. package/scripts/run/ship/run-ship-relaunch-cap.ts +70 -0
  765. package/scripts/run/ship/run-ship-removed-rows.ts +61 -0
  766. package/scripts/run/ship/run-ship-return.ts +123 -15
  767. package/scripts/run/ship/run-ship-review-steps.ts +105 -149
  768. package/scripts/run/ship/run-ship-review.ts +73 -6
  769. package/scripts/run/ship/run-ship-reviewer.ts +207 -0
  770. package/scripts/run/ship/run-ship-stage.ts +55 -6
  771. package/scripts/run/ship/run-ship-steps.ts +46 -15
  772. package/scripts/run/ship/run-ship-stop-cause.ts +135 -0
  773. package/scripts/run/ship/run-ship-stop-context.ts +206 -0
  774. package/scripts/run/ship/run-ship-stop-text.ts +11 -6
  775. package/scripts/run/ship/run-ship-sync.ts +57 -12
  776. package/scripts/run/ship/run-ship.ts +30 -2
  777. package/scripts/run/tidy/run-tidy-cli.ts +0 -4
  778. package/scripts/run/tidy/run-tidy-lanes.ts +3 -0
  779. package/scripts/run/tidy/run-tidy-main.ts +8 -0
  780. package/scripts/run/wake/run-wake-cli.ts +119 -100
  781. package/scripts/run/wake/run-wake-code.ts +83 -0
  782. package/scripts/run/wake/run-wake-driver.ts +19 -8
  783. package/scripts/run/wake/run-wake-loop.ts +34 -3
  784. package/scripts/run/wake/run-wake-main.ts +13 -0
  785. package/scripts/run/wake/run-wake-ports.ts +90 -0
  786. package/scripts/run/wake/run-wake-takeover.ts +66 -0
  787. package/scripts/run/wake/run-wake.ts +2 -1
  788. package/scripts/safe-chain/pack-hook.ts +2 -2
  789. package/scripts/safe-chain/preinstall-command.ts +2 -1
  790. package/scripts/safe-chain/project-config.ts +3 -9
  791. package/scripts/security/security-audit-main.ts +8 -0
  792. package/scripts/security/security-audit-provision-logic.ts +0 -11
  793. package/scripts/security/security-audit-provision-main.ts +12 -0
  794. package/scripts/security/security-audit-provision.ts +11 -26
  795. package/scripts/security/security-audit.ts +6 -7
  796. package/scripts/self-sync-guard/self-sync-guard-logic.ts +6 -13
  797. package/scripts/split/split-assess-cli.ts +2 -2
  798. package/scripts/split/split-assess.ts +15 -0
  799. package/scripts/split/split-measure.ts +65 -0
  800. package/scripts/sync/claude-settings-merge.ts +8 -15
  801. package/scripts/sync/directory-copy-guard.ts +4 -9
  802. package/scripts/sync/file-content.ts +78 -8
  803. package/scripts/sync/sync-ai-files.ts +3 -5
  804. package/scripts/sync/sync-configs.ts +11 -23
  805. package/scripts/sync/sync-hook-safety.ts +4 -10
  806. package/scripts/sync/sync-main.ts +11 -0
  807. package/scripts/sync/sync.ts +25 -37
  808. package/scripts/test/test-declared-changed.ts +2 -2
  809. package/scripts/test/test-declared.ts +1 -1
  810. package/scripts/test/test-e2e-guard.ts +55 -6
  811. package/scripts/test/test-e2e-stamp.ts +38 -0
  812. package/scripts/test/test-pinned-logic.ts +145 -0
  813. package/scripts/test/test-pinned-main.ts +78 -0
  814. package/scripts/test/test-pinned.ts +100 -0
  815. package/scripts/test/test-read-map.ts +264 -0
  816. package/scripts/test/test-read-recording.ts +91 -0
  817. package/scripts/test/test-read-trace.ts +148 -0
  818. package/scripts/test/test-red-main.ts +12 -0
  819. package/scripts/test/test-red.ts +12 -30
  820. package/scripts/test/test-related-main.ts +18 -0
  821. package/scripts/test/test-related-record.ts +119 -0
  822. package/scripts/test/test-related-scope.ts +229 -43
  823. package/scripts/test/test-related.ts +300 -22
  824. package/scripts/test/test-unit-guard-main.ts +15 -0
  825. package/scripts/test/test-unit-guard.ts +54 -21
  826. package/scripts/test/unit-count-file.ts +37 -0
  827. package/scripts/test/unit-run-marker.ts +162 -0
  828. package/scripts/test/unit-setup-files.ts +51 -0
  829. package/scripts/test/unit-worker-share.ts +71 -137
  830. package/scripts/test/whole-suite-files.ts +63 -0
  831. package/scripts/time-runtime/time-background.ts +20 -2
  832. package/scripts/time-runtime/time-bundles.ts +4 -3
  833. package/scripts/time-runtime/time-density-hook.ts +8 -6
  834. package/scripts/time-runtime/time-followup-stage.ts +1 -3
  835. package/scripts/time-runtime/time-format.ts +5 -28
  836. package/scripts/time-runtime/time-markers.ts +10 -1
  837. package/scripts/time-runtime/time-shell.ts +126 -14
  838. package/scripts/time-runtime/time-spans.ts +1 -0
  839. package/scripts/time-runtime/time-tool-call.ts +7 -0
  840. package/scripts/time-runtime/time-transcript-line.ts +49 -62
  841. package/scripts/uninstall/uninstall.ts +1 -1
  842. package/scripts/version/bump-version-main.ts +12 -0
  843. package/scripts/version/bump-version.ts +25 -25
  844. package/scripts/version/effective-upstream.ts +6 -12
  845. package/scripts/version/latest-corepack.ts +17 -32
  846. package/scripts/version/latest-if-required-cli.ts +93 -0
  847. package/scripts/version/latest-lane-guard-main.ts +8 -0
  848. package/scripts/version/latest-lane-guard.ts +0 -4
  849. package/scripts/version/latest-scope-cli.ts +0 -9
  850. package/scripts/version/latest-scope-main.ts +12 -0
  851. package/scripts/version/latest-update.ts +5 -5
  852. package/scripts/version/npm-registry.ts +44 -6
  853. package/scripts/version/publishable-range-check.ts +5 -16
  854. package/scripts/version/release-age.ts +1 -1
  855. package/scripts/version/release-hold.ts +1 -1
  856. package/scripts/version/release-window.ts +38 -0
  857. package/scripts/version/running-binary.ts +1 -1
  858. package/scripts/version/safe-chain-version-update.ts +3 -8
  859. package/scripts/version/version-targets.ts +6 -28
  860. package/templates/dependabot.yml +29 -0
  861. package/templates/gitignore +10 -3
  862. package/templates/pnpm-workspace.basic.yaml +1 -1
  863. package/templates/sonar-project.properties +3 -2
  864. package/templates/workflows/ci.yml +12 -4
  865. package/templates/workflows/github-release.yml +4 -0
  866. package/tsconfig.sonar.json +1 -1
  867. package/.ncurc.json +0 -3
  868. package/dist/hooks/batch-guard.js +0 -29
  869. package/dist/hooks/chunk-43ZHT22P.js +0 -3495
  870. package/dist/hooks/chunk-CDY4NFQG.js +0 -15
  871. package/dist/hooks/chunk-EUMACUK2.js +0 -2038
  872. package/dist/hooks/chunk-H5HVWYXK.js +0 -359
  873. package/dist/hooks/chunk-IIGFYXKC.js +0 -7104
  874. package/dist/hooks/chunk-IX6TTTI6.js +0 -95
  875. package/dist/hooks/chunk-J47HU5H5.js +0 -237
  876. package/dist/hooks/chunk-K4EOONYM.js +0 -45
  877. package/dist/hooks/chunk-K4LMBQC2.js +0 -68
  878. package/dist/hooks/chunk-SHGPANFB.js +0 -56
  879. package/dist/hooks/chunk-YHBZAJSV.js +0 -79
  880. package/dist/hooks/chunk-YYPI7SJZ.js +0 -131
  881. package/dist/hooks/duplicate-read-guard.js +0 -30
  882. package/dist/hooks/investigation-guard.js +0 -32
  883. package/scripts/backlog/backlog-stalled-cli.ts +0 -30
  884. package/scripts/cost-runtime/cost-format.ts +0 -29
  885. package/scripts/init/basic-path-migration.ts +0 -24
  886. package/scripts/issue/issue-backlinks-cli.ts +0 -93
  887. package/scripts/josh/josh-commands-guard.ts +0 -38
  888. package/scripts/lint/cross-file-recheck.ts +0 -155
  889. package/scripts/registry-migration/migrate-logic.ts +0 -237
  890. package/scripts/registry-migration/migrate.ts +0 -292
  891. package/scripts/registry-migration/user-npmrc.ts +0 -15
  892. package/scripts/rules/rule-guard.ts +0 -23
  893. package/scripts/rules/rule-registry-rows.ts +0 -282
  894. package/scripts/rules/rule-registry.ts +0 -109
  895. package/scripts/run/run-stranded-cli.ts +0 -27
@@ -0,0 +1,195 @@
1
+ import { availableParallelism } from 'node:os'
2
+ import { bounded_pool } from '#scripts/lib/bounded-pool'
3
+ import { buffered_process } from '#scripts/lib/buffered-process'
4
+ import { unit_worker_share } from '#scripts/test/unit-worker-share'
5
+ import { check_cpu, type CheckCpu } from './check-cpu'
6
+ import { core_budget, type Admission } from './core-budget'
7
+ import { free_cores } from './free-cores'
8
+ import { gate_plan, type GatePlan } from './gate-plan'
9
+ import type { CheckClaim, GateStep, GateStepResult } from './gate-report'
10
+ import { build_gate_step, with_granted_workers } from './gate-steps'
11
+ import { project_checks } from './project-checks'
12
+
13
+ // Running the gate's checks: each one under its place in the machine-wide budget, a reused one
14
+ // (`check-reuse.ts`) without starting it. `verification-gate.ts` decides what runs and records the
15
+ // outcome; this module only runs it.
16
+
17
+ // `cpu` is the gate's shared reader, so concurrent checks each take their own growth; a lone call
18
+ // reads its child alone from a baseline of its own.
19
+ async function run_gate_step(
20
+ step: GateStep,
21
+ cpu: CheckCpu = check_cpu.check_cpu_reader(),
22
+ ): Promise<GateStepResult> {
23
+ if (step.skip_reason !== undefined) {
24
+ return {
25
+ label: step.label,
26
+ command: step.command_args.join(' '),
27
+ output: project_checks.skip_notice('check', step.skip_reason),
28
+ exit_code: 0,
29
+ elapsed_ms: 0,
30
+ }
31
+ }
32
+
33
+ const result = await buffered_process.run_buffered_process(
34
+ step.command_args,
35
+ step.cwd === undefined ? {} : { cwd: step.cwd },
36
+ )
37
+
38
+ return { label: step.label, command: step.command_args.join(' '), ...result, cpu_ms: cpu() }
39
+ }
40
+
41
+ // This gate's share of the machine, resolved once at the gate's entry and carried down as one value.
42
+ // `available_cores` is the budget every check reserves against; `is_reserved`
43
+ // is false for a gate nested inside another gate's unit suite — this repository's own gate tests — so
44
+ // the outer gate reserves and every gate beneath it does not. Captured before this gate sets
45
+ // `JOSH_UNIT_RUN_MARKED`, which is why it is read at entry rather than re-derived here.
46
+ interface BudgetContext {
47
+ available_cores: number
48
+ is_reserved: boolean
49
+ }
50
+
51
+ function default_budget(): BudgetContext {
52
+ return {
53
+ available_cores: availableParallelism(),
54
+ is_reserved: !unit_worker_share.is_nested_run() && !core_budget.is_held(),
55
+ }
56
+ }
57
+
58
+ // A gate step paired with the cores it reserves from the machine-wide budget while it runs.
59
+ // The weight travels with the step so `run_gate_steps` never has to re-pair a
60
+ // step with its check by index.
61
+ interface ReservedStep {
62
+ step: GateStep
63
+ weight: number
64
+ memory_mb: number
65
+ // The plan's `--maxWorkers` for the unit suite, the width the free memory bounds once it is admitted.
66
+ worker_cap: number | undefined
67
+ // When the check's own green record was taken, for a check `check-reuse.ts` found reusable.
68
+ reused_at: string | undefined
69
+ }
70
+
71
+ // The checks this gate reuses, each mapped to when it was last green.
72
+ type ReusedChecks = ReadonlyMap<string, string>
73
+
74
+ async function build_reserved_steps(
75
+ plan: GatePlan,
76
+ available_cores: number,
77
+ reused: ReusedChecks,
78
+ ): Promise<ReadonlyArray<ReservedStep>> {
79
+ return await Promise.all(
80
+ plan.checks.map(async (check) => ({
81
+ step: await build_gate_step(check, process.cwd(), plan),
82
+ weight: gate_plan.check_weight(check, plan, available_cores),
83
+ memory_mb: gate_plan.check_memory(check, plan, available_cores),
84
+ worker_cap: plan.unit_worker_cap,
85
+ reused_at: reused.get(check.label),
86
+ })),
87
+ )
88
+ }
89
+
90
+ // A reused check starts no process and claims no core: its result is the record's, and the empty
91
+ // output is what that record was written from (`gate_report.has_nothing_to_say`).
92
+ function reused_result(step: GateStep, reused_at: string): GateStepResult {
93
+ return {
94
+ label: step.label,
95
+ command: step.command_args.join(' '),
96
+ output: '',
97
+ exit_code: 0,
98
+ elapsed_ms: 0,
99
+ reused_at,
100
+ }
101
+ }
102
+
103
+ // What the check asked the budget for and what it ran at, for its ledger row (`gate-ledger.ts`).
104
+ function claim_of(requested: number, admission: Admission): CheckClaim {
105
+ return {
106
+ requested,
107
+ granted: admission.granted ?? requested,
108
+ waited_ms: admission.waited_ms ?? 0,
109
+ }
110
+ }
111
+
112
+ // **The unit step's width is bounded by the free memory too** (joshuafolkken/kit#4528). The plan's cap
113
+ // and the granted width are sized from the cores alone, and the `--maxWorkers` they become skips the
114
+ // guard's own reading (`test-unit-guard.ts`), so the memory is read here, once the claim is admitted
115
+ // and the suite is about to start. The free cores are not applied: the admission has already narrowed
116
+ // the claim to them (joshuafolkken/kit#4167).
117
+ async function admitted_step(
118
+ reserved: ReservedStep,
119
+ admission: Admission,
120
+ available_cores: number,
121
+ ): Promise<GateStep> {
122
+ if (reserved.step.label !== gate_plan.UNIT_LABEL) return reserved.step
123
+
124
+ const { memory_workers } = await free_cores.read({ available_cores })
125
+ const asked = admission.granted ?? reserved.worker_cap
126
+ const workers = unit_worker_share.cap_to_free(asked, memory_workers, available_cores)
127
+
128
+ return with_granted_workers(reserved.step, workers)
129
+ }
130
+
131
+ // **A nested gate takes no reservation, and the budget is what makes that necessary rather than
132
+ // merely tidy**. The unit step spawns the suite, which runs this repository's
133
+ // own gate tests; each of those is a gate inside the outer gate's unit reservation, and a place it
134
+ // claimed would wait for cores the outer gate cannot free until the suite — this test included —
135
+ // finishes.
136
+ async function run_reserved_step(
137
+ reserved: ReservedStep,
138
+ budget: BudgetContext,
139
+ cpu: CheckCpu,
140
+ ): Promise<GateStepResult> {
141
+ if (reserved.reused_at !== undefined) return reused_result(reserved.step, reserved.reused_at)
142
+ if (!budget.is_reserved) return await run_gate_step(reserved.step, cpu)
143
+
144
+ return await core_budget.with_core_reservation(
145
+ reserved.weight,
146
+ async (admission) => ({
147
+ ...(await run_gate_step(
148
+ await admitted_step(reserved, admission, budget.available_cores),
149
+ cpu,
150
+ )),
151
+ budget_note: core_budget.describe_overflow(admission),
152
+ claim: claim_of(reserved.weight, admission),
153
+ }),
154
+ {
155
+ budget: budget.available_cores,
156
+ memory_mb: reserved.memory_mb,
157
+ command: `gate ${reserved.step.label}`,
158
+ is_unit: reserved.step.label === gate_plan.UNIT_LABEL,
159
+ },
160
+ )
161
+ }
162
+
163
+ // `bounded_pool` rather than a bare `Promise.all`, so the plan's `concurrency` is what decides how
164
+ // many run at once. **The all-failures-in-one-pass property survives the
165
+ // change** because no check ever rejects: `buffered_process` reports a non-zero exit as a value, so
166
+ // the pool's first-failure abort — written for callers that spawn real Claude sessions — never
167
+ // fires here and every queued check still runs. Results come back in input order however they
168
+ // finished, which is what keeps the printed sections in declaration order. Each step first claims its
169
+ // place in the machine-wide budget and waits while the budget is full.
170
+ async function run_gate_steps(
171
+ plan: GatePlan,
172
+ budget: BudgetContext = default_budget(),
173
+ reused: ReusedChecks = new Map(),
174
+ ): Promise<ReadonlyArray<GateStepResult>> {
175
+ const reserved = await build_reserved_steps(plan, budget.available_cores, reused)
176
+ const cpu = check_cpu.check_cpu_reader()
177
+
178
+ // **The checks run under the held mark, so a check's own dispatch claims nothing**.
179
+ // Each check is a `pnpm josh <target>` child, and a target that declares
180
+ // a weight would otherwise claim a second place for the cores reserved for it here. A nested gate
181
+ // sets the mark too, since its checks are covered by the outer gate's reservation.
182
+ return await core_budget.with_held_mark(
183
+ async () =>
184
+ await bounded_pool.bounded_map(
185
+ reserved,
186
+ plan.concurrency,
187
+ async (entry) => await run_reserved_step(entry, budget, cpu),
188
+ ),
189
+ )
190
+ }
191
+
192
+ const gate_run_steps = { default_budget, run_gate_step, run_gate_steps }
193
+
194
+ export type { BudgetContext, ReusedChecks }
195
+ export { gate_run_steps }
@@ -64,10 +64,19 @@ const FORCE_FLAG = '--force'
64
64
  // rewritten by the hook's own install each cost minutes before anyone could tell them apart.
65
65
  type GateReuse = { stamp: FileMapStamp } | { miss: string }
66
66
 
67
+ // The fingerprint of every declared check's tools and environment (`verification-inputs.ts`).
68
+ const INPUTS_MOVED = 'a checked tool or environment variable changed since the green gate'
69
+
67
70
  function base_moved(recorded: string | undefined, base: string): string {
68
71
  return `the merge base moved since the green gate (${recorded ?? 'none'} → ${base})`
69
72
  }
70
73
 
74
+ function stamp_miss(stamp: FileMapStamp, base: string): string | undefined {
75
+ if (stamp.base !== base) return base_moved(stamp.base, base)
76
+
77
+ return review_stamps.gate_stamp.describes_inputs(stamp) ? undefined : INPUTS_MOVED
78
+ }
79
+
71
80
  function gate_reuse(
72
81
  tree: Record<string, string>,
73
82
  base: string | undefined,
@@ -79,9 +88,10 @@ function gate_reuse(
79
88
  const stamp = review_brief.matching_stamp(review_stamps.gate_stamp.read(source), tree)
80
89
 
81
90
  if (stamp === undefined) return { miss: 'no green gate record matches the changed files' }
82
- if (stamp.base !== base) return { miss: base_moved(stamp.base, base) }
83
91
 
84
- return { stamp }
92
+ const miss = stamp_miss(stamp, base)
93
+
94
+ return miss === undefined ? { stamp } : { miss }
85
95
  }
86
96
 
87
97
  function stamp_of(reuse: GateReuse): FileMapStamp | undefined {
@@ -42,6 +42,17 @@ async function build_gate_step(
42
42
  return { label: check.label, command_args, cwd, skip_reason }
43
43
  }
44
44
 
45
+ // The unit step at a narrower worker count: the one its claim was admitted at past the wait cap
46
+ // (`core_admission.narrowed_weight`), or the one the free memory holds (`gate-run-steps.ts`). Any
47
+ // other step, or one left as asked, is returned unchanged.
48
+ function with_granted_workers(step: GateStep, granted: number | undefined): GateStep {
49
+ if (granted === undefined || step.label !== UNIT_LABEL) return step
50
+
51
+ const kept = step.command_args.filter((argument) => !argument.startsWith(`${UNIT_WORKER_FLAG}=`))
52
+
53
+ return { ...step, command_args: [...kept, `${UNIT_WORKER_FLAG}=${String(granted)}`] }
54
+ }
55
+
45
56
  async function build_gate_steps(
46
57
  start_directory: string,
47
58
  plan: GatePlan = gate_plan.resolve_gate_plan(),
@@ -51,4 +62,4 @@ async function build_gate_steps(
51
62
  )
52
63
  }
53
64
 
54
- export { build_gate_step, build_gate_steps, UNIT_WORKER_FLAG }
65
+ export { build_gate_step, build_gate_steps, UNIT_WORKER_FLAG, with_granted_workers }
@@ -0,0 +1,55 @@
1
+ // **The environment mark that says a parent already holds this process's cores**
2
+ // `josh gate` reserves per check and then spawns `pnpm josh lint`. Without
3
+ // the mark, that child's own dispatch would claim a second place for the cores its parent already
4
+ // holds. Every holder sets it, and every child inherits it through the environment and claims nothing.
5
+ const HELD_KEY = 'JOSH_CORE_RESERVED'
6
+ const HELD_VALUE = '1'
7
+ // The ledger key of the claim a command holds for its children (`core_budget.with_command_reservation`),
8
+ // so a child reading the machine can tell that claim's admitted, not-yet-busy weight from running load.
9
+ const HELD_RESERVATION_KEY = 'JOSH_CORE_RESERVATION'
10
+
11
+ function is_held(): boolean {
12
+ return process.env[HELD_KEY] === HELD_VALUE
13
+ }
14
+
15
+ // The ledger key of the one claim a parent command holds for this process, `undefined` where none does.
16
+ function held_reservation(): string | undefined {
17
+ const key = process.env[HELD_RESERVATION_KEY] ?? ''
18
+
19
+ return key === '' ? undefined : key
20
+ }
21
+
22
+ // A function of its own so the restoring write does not sit after an `await`, where
23
+ // `require-atomic-updates` reads any write to `process` as a possible race — the reason `josh.ts`
24
+ // gives `record_exit_code`.
25
+ function set_held_mark(value: string, reservation: string): void {
26
+ process.env[HELD_KEY] = value
27
+ process.env[HELD_RESERVATION_KEY] = reservation
28
+ }
29
+
30
+ // Marks this process, and every child it spawns, as running inside a held reservation — `reservation`
31
+ // names its ledger key where one claim covers them all. The previous values come back afterwards, so a
32
+ // nested holder never clears the mark its outer holder set.
33
+ async function with_held_mark<T>(run: () => Promise<T>, reservation = ''): Promise<T> {
34
+ const previous = process.env[HELD_KEY] ?? ''
35
+ const previous_reservation = process.env[HELD_RESERVATION_KEY] ?? ''
36
+
37
+ set_held_mark(HELD_VALUE, reservation)
38
+
39
+ try {
40
+ return await run()
41
+ } finally {
42
+ set_held_mark(previous, previous_reservation)
43
+ }
44
+ }
45
+
46
+ const held_mark = {
47
+ HELD_KEY,
48
+ HELD_RESERVATION_KEY,
49
+ HELD_VALUE,
50
+ held_reservation,
51
+ is_held,
52
+ with_held_mark,
53
+ }
54
+
55
+ export { held_mark }
@@ -0,0 +1,42 @@
1
+ import { readFileSync } from 'node:fs'
2
+ import path from 'node:path'
3
+ import { stamp_file } from '#scripts/josh/stamp-file'
4
+
5
+ // **The one fingerprint every kept result is computed with** (joshuafolkken/kit#4497). A reuse of a
6
+ // verdict holds only while what it read holds, and each reader of a verdict once computed that on its
7
+ // own — the ESLint cache's import closure, the test-read map's dirty files, the gate's tool versions —
8
+ // so a miss in one (joshuafolkken/kit#4407, #4415, #4423, #4425) was a miss nowhere else. Every one now
9
+ // digests a file, a set of files and a set of named entries here.
10
+
11
+ // The digest of a path that does not exist, or cannot be read, so it still differs from any content.
12
+ const ABSENT = 'absent'
13
+
14
+ function of_content(content: Buffer | string): string {
15
+ return stamp_file.digest(content)
16
+ }
17
+
18
+ // One digest over `entries`, independent of their order.
19
+ function of_entries(entries: Iterable<string>): string {
20
+ return of_content([...entries].toSorted((left, right) => left.localeCompare(right)).join('\n'))
21
+ }
22
+
23
+ function of_file(file_path: string): string {
24
+ try {
25
+ return of_content(readFileSync(file_path))
26
+ } catch {
27
+ return ABSENT
28
+ }
29
+ }
30
+
31
+ // Each of `relatives` (relative to `root`) keyed to the digest of its content, in path order.
32
+ function of_files(root: string, relatives: Iterable<string>): Record<string, string> {
33
+ const sorted = [...new Set(relatives)].toSorted((left, right) => left.localeCompare(right))
34
+
35
+ return Object.fromEntries(
36
+ sorted.map((relative) => [relative, of_file(path.join(root, relative))]),
37
+ )
38
+ }
39
+
40
+ const input_fingerprint = { ABSENT, of_entries, of_file, of_files }
41
+
42
+ export { input_fingerprint }
@@ -1,5 +1,5 @@
1
1
  import { readFile } from 'node:fs/promises'
2
- import { availableParallelism, cpus, totalmem } from 'node:os'
2
+ import { availableParallelism, cpus, loadavg, totalmem } from 'node:os'
3
3
  import { PROBE_TIMEOUT_MS } from '#scripts/lib/timeouts'
4
4
  import { execa } from 'execa'
5
5
 
@@ -24,19 +24,20 @@ import { execa } from 'execa'
24
24
  // admits without looking at memory, exactly as before.
25
25
  //
26
26
  // **`run:board` draws its machine gauges from the same reading**, so what the
27
- // board shows a person is what the gate admits against. The board takes a sample with no window and
27
+ // board shows a person is what the gate admits against — the gate reading the free memory as none
28
+ // while the board's pressure and swap gauges show why. The board takes a sample with no window and
28
29
  // draws the difference from its previous one. `lane:sample` records the memory half of it, so the
29
30
  // lane-limit measurement sets the same figures beside the lane count.
30
31
 
31
32
  // The window the busy cores are measured over: long enough that one scheduler tick does not dominate it,
32
33
  // short enough that a solo admission is not visibly delayed.
33
34
  const SAMPLE_WINDOW_MS = 250
34
- // **The background a developer machine always carries, which the gate's weights were measured beside.**
35
- // On 2026-10-07 the 11-core machine idled at about 1.5 cores outside `josh` — Claude sessions 0.55, the
36
- // window server 0.47, a browser 0.5. The solo gate's weights sum to exactly the core count and were
37
- // measured with that load present, so only what exceeds it is load the budget must give way to;
38
- // counting the baseline would defer a solo gate's unit suite on every run.
39
- const BASELINE_CORES = 2
35
+ // **Run-queue load outside the ledger past this many times the cores holds the first waiter too**
36
+ // (joshuafolkken/kit#4361). The first waiter ignores outside load (joshuafolkken/kit#4313), and lanes took
37
+ // the 11-core machine to a load average of 25–34. Twice the cores is loose on purpose: the one-core
38
+ // editor load #4313 stopped holding a solo gate stays far below it, so neither its starvation nor the
39
+ // lanes' speed comes back, while a machine whose queue beyond the ledger passes two per core waits.
40
+ const OVERLOAD_FACTOR = 2
40
41
  const BYTES_PER_MB = 1_048_576
41
42
  const KB_PER_MB = 1024
42
43
  const PERCENT = 100
@@ -50,29 +51,56 @@ const PAGE_SIZE_ARGUMENTS = ['PAGESIZE']
50
51
  // every second. `kern.memorystatus_level` is the kernel's own memory-pressure figure: the percentage of
51
52
  // memory still available, compressible and purgeable pages included — what `os.freemem()` leaves out on
52
53
  // macOS, where it reads near zero on a machine with gigabytes to spare. The swapper counters are the
53
- // pages swapped in and out since boot, `vm_stat`'s `Swapins` / `Swapouts`. The names stay in the output
54
+ // pages swapped in and out since boot, `vm_stat`'s `Swapins` / `Swapouts`; `vm.compressor_input_bytes` is
55
+ // the bytes the compressor has taken in since boot, `vm_stat`'s `Compressions`. The names stay in the output
54
56
  // (no `-n`), so a name an older macOS lacks drops only its own line.
55
57
  const LEVEL_NAME = 'kern.memorystatus_level'
56
58
  const SWAP_IN_NAME = 'vm.compressor.swapper.swapins_total'
57
59
  const SWAP_OUT_NAME = 'vm.compressor.swapper.swapouts_total'
60
+ const COMPRESSED_NAME = 'vm.compressor_input_bytes'
58
61
  const PAGE_SIZE_NAME = 'hw.pagesize'
59
62
  // The kernel's memory-pressure verdict — 1 normal, 2 warning, 4 critical — the one Activity Monitor
60
63
  // colors its "memory pressure" graph by.
61
64
  const PRESSURE_NAME = 'kern.memorystatus_vm_pressure_level'
62
- const SYSCTL_ARGUMENTS = [LEVEL_NAME, SWAP_IN_NAME, SWAP_OUT_NAME, PAGE_SIZE_NAME, PRESSURE_NAME]
65
+ // **Only critical holds; warning is sticky** (joshuafolkken/kit#4199). On macOS the verdict can stay at
66
+ // warning for hours after the pressure passed, so a hold on warning never lifts. What is pressured right
67
+ // now shows in the free figure and the swap and compressor traffic; the verdict adds only critical.
68
+ const PRESSURE_HOLD = 4
69
+ // The swap traffic across one window that reads as pressure — 64 MB a second paged to disk. A machine
70
+ // that swapped once still pages a few megabytes back in as old pages are touched.
71
+ const SWAP_PRESSURE_MB = 16
72
+ // The compressor traffic across one window that reads as pressure. An idle machine compresses nothing
73
+ // across a window; the 2026-10-16 thrash compressed about 240,000 16 KB pages every three seconds, about
74
+ // 310 MB a window, with no swap figure to show for it.
75
+ const COMPRESSION_PRESSURE_MB = 64
76
+ const SYSCTL_ARGUMENTS = [
77
+ LEVEL_NAME,
78
+ SWAP_IN_NAME,
79
+ SWAP_OUT_NAME,
80
+ COMPRESSED_NAME,
81
+ PAGE_SIZE_NAME,
82
+ PRESSURE_NAME,
83
+ ]
63
84
  const SYSCTL_LINE = /^(?<name>[\w.]+): (?<value>\d+)$/gmu
64
85
 
86
+ // `memory_pressured` says why `available_mb` read none, so a claim that waits can name the pressure.
87
+ // `run_queue` is the one-minute load average: the busy cores stop at the core count, so only the queue
88
+ // tells a machine at twice its cores from one at once (`is_overloaded`).
65
89
  interface MachineReading {
66
90
  busy_cores: number | undefined
67
91
  available_mb: number | undefined
92
+ memory_pressured?: boolean | undefined
93
+ run_queue?: number | undefined
68
94
  }
69
95
 
70
96
  // The memory half of a reading. `swapped_mb` is a counter — every page swapped in or out since boot —
71
- // so a rate is the difference between two readings. `pressure_level` is read on macOS only.
97
+ // so a rate is the difference between two readings, and so is `compressed_mb`, every byte compressed
98
+ // since boot. `pressure_level` and `compressed_mb` are read on macOS only.
72
99
  interface MemoryReading {
73
100
  available_mb: number | undefined
74
101
  swapped_mb: number | undefined
75
102
  pressure_level: number | undefined
103
+ compressed_mb?: number | undefined
76
104
  }
77
105
 
78
106
  // What the ledger's admitted reservations declare — the part of the machine's load already accounted for.
@@ -81,9 +109,15 @@ interface LedgerLoad {
81
109
  memory_mb: number
82
110
  }
83
111
 
112
+ // `busy_excess` is the measured cores beyond what the ledger declares — what `cores` gave up to load the
113
+ // ledger does not hold, so a claim that waits on it can name the CPU as saturated. `is_overloaded` lifts
114
+ // the first waiter's exemption from that load (`core_admission.is_admitted`).
84
115
  interface MachineBudget {
85
116
  cores: number
86
117
  memory_mb: number
118
+ memory_pressured?: boolean | undefined
119
+ busy_excess?: number | undefined
120
+ is_overloaded?: boolean | undefined
87
121
  }
88
122
 
89
123
  interface CpuTimes {
@@ -141,10 +175,10 @@ function swapped_pages(
141
175
  return pages_in === undefined || pages_out === undefined ? undefined : pages_in + pages_out
142
176
  }
143
177
 
144
- function swapped_mb(pages: number | undefined, page_bytes: number | undefined): number | undefined {
145
- if (pages === undefined || page_bytes === undefined) return undefined
178
+ function mb_of(units: number | undefined, unit_bytes: number | undefined): number | undefined {
179
+ if (units === undefined || unit_bytes === undefined) return undefined
146
180
 
147
- return (pages * page_bytes) / BYTES_PER_MB
181
+ return (units * unit_bytes) / BYTES_PER_MB
148
182
  }
149
183
 
150
184
  // What was swapped between two readings of the counter. A counter that went back — a reboot between
@@ -163,11 +197,12 @@ function parse_darwin_memory(output: string, total_bytes: number): MemoryReading
163
197
  return {
164
198
  available_mb:
165
199
  level === undefined ? undefined : (level / PERCENT) * (total_bytes / BYTES_PER_MB),
166
- swapped_mb: swapped_mb(
200
+ swapped_mb: mb_of(
167
201
  swapped_pages(values.get(SWAP_IN_NAME), values.get(SWAP_OUT_NAME)),
168
202
  values.get(PAGE_SIZE_NAME),
169
203
  ),
170
204
  pressure_level: values.get(PRESSURE_NAME),
205
+ compressed_mb: mb_of(values.get(COMPRESSED_NAME), 1),
171
206
  }
172
207
  }
173
208
 
@@ -187,7 +222,7 @@ function pages_of(pattern: RegExp, vmstat: string): number | undefined {
187
222
  function parse_linux_swapped(vmstat: string, page_bytes: number): number | undefined {
188
223
  const pages = swapped_pages(pages_of(LINUX_SWAP_IN, vmstat), pages_of(LINUX_SWAP_OUT, vmstat))
189
224
 
190
- return swapped_mb(pages, page_bytes)
225
+ return mb_of(pages, page_bytes)
191
226
  }
192
227
 
193
228
  async function settled<T>(read: () => Promise<T>): Promise<T | undefined> {
@@ -256,56 +291,114 @@ async function default_sleep(ms: number): Promise<void> {
256
291
  })
257
292
  }
258
293
 
294
+ // Whether a counter gained more than `limit` MB across the window; an unread counter gained nothing.
295
+ function moved_over(from: number | undefined, to: number | undefined, limit: number): boolean {
296
+ return (swapped_between(from, to) ?? 0) > limit
297
+ }
298
+
299
+ function is_pressured(before: MemoryReading, after: MemoryReading): boolean {
300
+ return (
301
+ (after.pressure_level ?? 0) >= PRESSURE_HOLD ||
302
+ moved_over(before.swapped_mb, after.swapped_mb, SWAP_PRESSURE_MB) ||
303
+ moved_over(before.compressed_mb, after.compressed_mb, COMPRESSION_PRESSURE_MB)
304
+ )
305
+ }
306
+
307
+ // **Only a reading the kernel calls critical has nothing free to admit against.** Swap and compressor
308
+ // traffic across the window used to answer no free memory too (joshuafolkken/kit#3943), but this machine
309
+ // swaps out 0.4–1.3 TB a day as a matter of course, so that traffic held about a third of every wait
310
+ // with memory to spare (joshuafolkken/kit#4313). A claim now waits on memory only when the free figure
311
+ // falls short of what it declares; the traffic still names the wait as pressure (`memory_pressured`),
312
+ // and holds a claim past the shortfall that running alone or the wait cap would otherwise start
313
+ // (`core_admission.is_swap_held`, joshuafolkken/kit#4451).
314
+ function pressured_available(after: MemoryReading): number | undefined {
315
+ if (after.available_mb === undefined) return undefined
316
+
317
+ return (after.pressure_level ?? 0) >= PRESSURE_HOLD ? 0 : after.available_mb
318
+ }
319
+
320
+ // Memory is read at both ends of the window, so the swap counter's difference is the activity during it.
259
321
  async function read_machine(
260
322
  sleep: (ms: number) => Promise<void> = default_sleep,
261
323
  ): Promise<MachineReading> {
262
324
  const before = cpu_times()
263
- const [memory] = await Promise.all([read_memory(), sleep(SAMPLE_WINDOW_MS)])
264
- const busy_cores = is_unquoted()
265
- ? busy_cores_between(before, cpu_times(), cpus().length)
266
- : undefined
325
+ const [memory_before] = await Promise.all([read_memory(), sleep(SAMPLE_WINDOW_MS)])
326
+ const memory_after = await read_memory()
327
+ const is_host = is_unquoted()
328
+ const busy_cores = is_host ? busy_cores_between(before, cpu_times(), cpus().length) : undefined
267
329
 
268
- return { busy_cores, available_mb: memory.available_mb }
330
+ return {
331
+ busy_cores,
332
+ run_queue: is_host ? loadavg()[0] : undefined,
333
+ available_mb: pressured_available(memory_after),
334
+ memory_pressured: is_pressured(memory_before, memory_after),
335
+ }
269
336
  }
270
337
 
271
338
  async function read_sample(): Promise<MachineSample> {
272
339
  return { cpu: cpu_times(), memory: await read_memory(), total_mb: totalmem() / BYTES_PER_MB }
273
340
  }
274
341
 
275
- // The busy cores the ledger does not account for, beyond the baseline the weights were measured beside,
276
- // in whole cores — the budget is in whole cores, and a fraction of a core is not a core to give up.
342
+ // The busy cores the ledger does not account for, in whole cores — the budget is in whole cores, and a
343
+ // fraction of a core is not a core to give up.
344
+ //
345
+ // **Every busy core counts, the background included** (joshuafolkken/kit#4238). A baseline of two cores
346
+ // used to be exempt, so with 10 cores reserved and all 11 busy the reading saw no excess and admitted
347
+ // another claim onto a saturated CPU.
277
348
  function external_cores(busy_cores: number | undefined, ledger_cores: number): number {
278
349
  if (busy_cores === undefined) return 0
279
350
 
280
- return Math.floor(Math.max(0, busy_cores - ledger_cores - BASELINE_CORES))
351
+ return Math.floor(Math.max(0, busy_cores - ledger_cores))
281
352
  }
282
353
 
283
- // **The budget the ledger admits against: what is free plus what the ledger itself already holds.**
284
- // The admitted reservations' load is inside the reading, and the admission walk counts their declared
285
- // weight again, so it is added back — what is subtracted is only the load from outside the ledger. The
286
- // caller passes every admitted claim's cores but only the memory of claims past
287
- // `core_admission.RAMP_UP_MS`, whose tools have had time to allocate.
354
+ // The run queue beyond what the ledger declares, past `OVERLOAD_FACTOR` times the cores. The ledger's own
355
+ // claims running past their weight count as outside load. The load average trails by a minute, so a
356
+ // first waiter held here waits out the decay — only at a load already this far past the machine. A queue
357
+ // that could not be read, and Windows' constant zero, never hold.
358
+ function is_overloaded(
359
+ run_queue: number | undefined,
360
+ ledger_cores: number,
361
+ cores: number,
362
+ ): boolean {
363
+ if (run_queue === undefined) return false
364
+
365
+ return run_queue - ledger_cores > cores * OVERLOAD_FACTOR
366
+ }
367
+
368
+ // **The budget the ledger admits against: `cores − max(ledger, busy)` free, plus what the ledger itself
369
+ // already holds.** The admission walk counts the ledger's declared weight again, so it is added back —
370
+ // what is subtracted is only the busy load beyond it. A claim admitted moments ago is not busy yet, and
371
+ // the ledger's declared cores cover it. The caller passes every admitted claim's cores but only the
372
+ // memory of claims past `core_admission.RAMP_UP_MS`, whose tools have had time to allocate.
288
373
  // Memory that could not be read is no limit at all, the behavior before memory was read.
289
374
  function machine_budget(cores: number, reading: MachineReading, ledger: LedgerLoad): MachineBudget {
375
+ const busy_excess = external_cores(reading.busy_cores, ledger.cores)
376
+
290
377
  return {
291
- cores: cores - external_cores(reading.busy_cores, ledger.cores),
378
+ cores: Math.max(0, cores - busy_excess),
292
379
  memory_mb:
293
380
  reading.available_mb === undefined ? Infinity : reading.available_mb + ledger.memory_mb,
381
+ memory_pressured: reading.memory_pressured,
382
+ busy_excess,
383
+ is_overloaded: is_overloaded(reading.run_queue, ledger.cores, cores),
294
384
  }
295
385
  }
296
386
 
297
387
  const machine_capacity = {
298
- BASELINE_CORES,
299
388
  busy_cores_between,
300
389
  busy_share_between,
390
+ COMPRESSION_PRESSURE_MB,
301
391
  external_cores,
302
392
  machine_budget,
303
393
  parse_darwin_memory,
304
394
  parse_linux_available,
305
395
  parse_linux_swapped,
396
+ PRESSURE_HOLD,
397
+ pressured_available,
306
398
  read_machine,
307
399
  read_memory,
308
400
  read_sample,
401
+ SWAP_PRESSURE_MB,
309
402
  swapped_between,
310
403
  }
311
404