@joshuafolkken/kit 1.1010.0 → 1.1050.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 (350) hide show
  1. package/.claude/settings.json +1 -5
  2. package/.claude/skills/dependency-update/SKILL.md +6 -3
  3. package/.claude/skills/epic-commands/SKILL.md +46 -17
  4. package/.claude/skills/verify-ui/SKILL.md +1 -1
  5. package/.claude/skills/workflow-commands/SKILL.md +10 -25
  6. package/.claude/skills/workflow-commands/background-commands.md +1 -1
  7. package/.claude/skills/workflow-commands/backlogrun-child.md +6 -4
  8. package/.claude/skills/workflow-commands/backlogrun-lanes.md +1 -1
  9. package/.claude/skills/workflow-commands/backlogrun-park.md +6 -0
  10. package/.claude/skills/workflow-commands/backlogrun-progress.md +30 -36
  11. package/.claude/skills/workflow-commands/backlogrun-steps.md +16 -16
  12. package/.claude/skills/workflow-commands/backlogrun.md +3 -12
  13. package/.claude/skills/workflow-commands/chain-rule.md +2 -2
  14. package/.claude/skills/workflow-commands/followup-reference.md +2 -2
  15. package/.claude/skills/workflow-commands/fullrun-steps.md +4 -3
  16. package/.claude/skills/workflow-commands/fullrun.md +1 -1
  17. package/.claude/skills/workflow-commands/halfrun.md +2 -1
  18. package/.claude/skills/workflow-commands/into-target.md +1 -1
  19. package/.claude/skills/workflow-commands/issue-comments.md +1 -1
  20. package/.claude/skills/workflow-commands/observation-filing.md +80 -126
  21. package/.claude/skills/workflow-commands/pre-gate-cut.md +33 -36
  22. package/.claude/skills/workflow-commands/prerequisite.md +1 -1
  23. package/.claude/skills/workflow-commands/working-tree-hold.md +2 -2
  24. package/.codex/hooks.json +1 -5
  25. package/.github/workflows/auto-tag.yml +21 -0
  26. package/.github/workflows/publish.yml +9 -10
  27. package/.github/workflows/sonar-qube.yml +1 -1
  28. package/AGENTS.md +4 -25
  29. package/CLAUDE.md +24 -38
  30. package/GEMINI.md +4 -24
  31. package/README.md +22 -56
  32. package/dist/CLAUDE.md +24 -38
  33. package/dist/hooks/batch-guard.js +4 -4
  34. package/dist/hooks/{chunk-6PSTVOLH.js → chunk-5BK3K7V4.js} +114 -90
  35. package/dist/hooks/{chunk-PAXMLGSS.js → chunk-7VPDUBRN.js} +93 -175
  36. package/dist/hooks/{chunk-KPZN42RT.js → chunk-DMQN45FN.js} +3 -3
  37. package/dist/hooks/{chunk-WMIR5SNX.js → chunk-EJDX2TOB.js} +13 -3
  38. package/dist/hooks/{chunk-A2H5I2VD.js → chunk-GQ7KP45M.js} +2 -2
  39. package/dist/hooks/{chunk-4GDR2YTV.js → chunk-HJIISEAC.js} +4 -4
  40. package/dist/hooks/{chunk-AWTFKKFW.js → chunk-NAS4C7GP.js} +6 -33
  41. package/dist/hooks/{chunk-56LGMJJV.js → chunk-NJQOBE6L.js} +2 -2
  42. package/dist/hooks/{chunk-EZLHXKJ6.js → chunk-RLDX5SOC.js} +1222 -941
  43. package/dist/hooks/{chunk-GBJUERYK.js → chunk-WQ4OSBSS.js} +10 -3
  44. package/dist/hooks/codex-hook-adapter.js +10 -10
  45. package/dist/hooks/duplicate-read-guard.js +5 -5
  46. package/dist/hooks/format-edited.js +15 -34
  47. package/dist/hooks/investigation-guard.js +5 -5
  48. package/dist/hooks/pretool-guard.js +23 -16
  49. package/dist/hooks/stop-guard.js +21 -200
  50. package/dist/josh.js +42 -125
  51. package/dist/version/index.js +466 -42
  52. package/eslint/base.js +2 -11
  53. package/package.json +36 -10
  54. package/prompts/coding-standards.md +15 -290
  55. package/prompts/collaboration-workflow/cross-repo-epic.md +2 -51
  56. package/prompts/collaboration-workflow/epic-audit.md +2 -53
  57. package/prompts/collaboration-workflow/epic-bundle.md +2 -106
  58. package/prompts/collaboration-workflow/file-edits.md +6 -53
  59. package/prompts/collaboration-workflow/issue-template.md +4 -4
  60. package/prompts/collaboration-workflow/operating-rules.md +18 -75
  61. package/prompts/collaboration-workflow/principles.md +74 -0
  62. package/prompts/collaboration-workflow/residency.md +55 -15
  63. package/prompts/collaboration-workflow/rule-delivery.md +5 -46
  64. package/prompts/collaboration-workflow/shell-body.md +7 -9
  65. package/prompts/collaboration-workflow/turn-batching.md +21 -37
  66. package/prompts/collaboration-workflow/upstream-interrupt.md +1 -1
  67. package/prompts/collaboration-workflow/wip-cap.md +15 -18
  68. package/prompts/collaboration-workflow.md +22 -28
  69. package/prompts/sonar-hotspot-handling.md +1 -1
  70. package/scripts/adopt/adopt-logic.ts +2 -2
  71. package/scripts/adopt/adopt-toolkits.ts +3 -1
  72. package/scripts/adopt/adopt.ts +2 -2
  73. package/scripts/agent/agent-event.ts +2 -9
  74. package/scripts/agent/agent-exit-record.ts +2 -9
  75. package/scripts/auto-ok/auto-ok-cli.ts +9 -9
  76. package/scripts/backlog/backlog-budget-cli.ts +2 -6
  77. package/scripts/backlog/backlog-drive-cli.ts +20 -10
  78. package/scripts/backlog/backlog-drive.ts +50 -16
  79. package/scripts/backlog/backlog-next.ts +24 -8
  80. package/scripts/backlog/backlog-offer-cli.ts +6 -5
  81. package/scripts/backlog/backlog-plan-cli.ts +5 -1
  82. package/scripts/backlog/backlog-plan.ts +1 -1
  83. package/scripts/backlog/backlog-pool.ts +31 -11
  84. package/scripts/backlog/backlog-rank.ts +106 -0
  85. package/scripts/backlog/backlog-waves.ts +42 -29
  86. package/scripts/build/build-bin.ts +2 -1
  87. package/scripts/build/build-config-merge.ts +2 -1
  88. package/scripts/build/build-hooks.ts +31 -6
  89. package/scripts/build/build-managed-marker.ts +2 -1
  90. package/scripts/build/build-self-sync-guard.ts +2 -1
  91. package/scripts/build/build-version.ts +2 -1
  92. package/scripts/cases/cases-logic.ts +2 -6
  93. package/scripts/ci/pr-classification.ts +13 -11
  94. package/scripts/cost-runtime/cost-transcript.ts +4 -11
  95. package/scripts/delegation/delegation-policy.ts +11 -0
  96. package/scripts/doctor/doctor-consumer.ts +5 -12
  97. package/scripts/doctor/doctor-ports.ts +2 -2
  98. package/scripts/document/document-byte-budget.ts +13 -21
  99. package/scripts/document/document-section.ts +2 -6
  100. package/scripts/document/entry-read-budget.ts +6 -5
  101. package/scripts/{git/git-epic-add-body.ts → epic/epic-add-body.ts} +23 -23
  102. package/scripts/{git/git-epic-add-plan.ts → epic/epic-add-plan.ts} +23 -26
  103. package/scripts/{git/git-epic-add.ts → epic/epic-add.ts} +17 -17
  104. package/scripts/epic/epic-audit-cli.ts +4 -4
  105. package/scripts/epic/epic-audit-orphans.ts +2 -2
  106. package/scripts/epic/epic-audit-rationale.ts +1 -1
  107. package/scripts/epic/epic-audit.ts +1 -1
  108. package/scripts/{git/git-epic-body.ts → epic/epic-body.ts} +6 -6
  109. package/scripts/epic/epic-bundle-cli.ts +1 -1
  110. package/scripts/epic/epic-bundle.ts +2 -2
  111. package/scripts/epic/epic-candidate-confirm.ts +2 -1
  112. package/scripts/{git/git-epic-chains.ts → epic/epic-chains.ts} +4 -4
  113. package/{scripts-ai → scripts/epic}/epic-check.ts +5 -4
  114. package/{scripts-ai → scripts/epic}/epic-cli.ts +4 -4
  115. package/scripts/{git/git-epic-close-comment.ts → epic/epic-close-comment.ts} +9 -9
  116. package/scripts/{git/git-epic-close.ts → epic/epic-close.ts} +23 -19
  117. package/scripts/epic/epic-cross-repo.ts +21 -38
  118. package/scripts/{git/git-epic-decision.ts → epic/epic-decision.ts} +12 -14
  119. package/scripts/epic/epic-fetch.ts +3 -3
  120. package/scripts/epic/epic-graph.ts +3 -3
  121. package/scripts/epic/epic-index.ts +2 -2
  122. package/scripts/epic/epic-issue.ts +1 -1
  123. package/scripts/epic/epic-lane-offer.ts +11 -22
  124. package/scripts/epic/epic-next.ts +3 -3
  125. package/scripts/{git/git-epic-parse.ts → epic/epic-parse.ts} +3 -3
  126. package/scripts/{git/git-epic-promote.ts → epic/epic-promote.ts} +10 -10
  127. package/scripts/epic/epic-rank.ts +37 -0
  128. package/scripts/{git/git-epic-read.ts → epic/epic-read.ts} +9 -9
  129. package/scripts/{git/git-epic-reconcile.ts → epic/epic-reconcile.ts} +18 -20
  130. package/scripts/{git/git-epic-reference.ts → epic/epic-reference.ts} +4 -23
  131. package/scripts/epic/epic-relation-recheck.ts +4 -3
  132. package/scripts/{git/git-epic-relations.ts → epic/epic-relations.ts} +5 -5
  133. package/scripts/{git/git-epic-remove-plan.ts → epic/epic-remove-plan.ts} +17 -19
  134. package/scripts/{git/git-epic-remove.ts → epic/epic-remove.ts} +13 -13
  135. package/scripts/{git/git-epic-run.ts → epic/epic-run.ts} +27 -27
  136. package/scripts/{git/git-epic-sections.ts → epic/epic-sections.ts} +6 -6
  137. package/scripts/{git/git-epic-shape.ts → epic/epic-shape.ts} +7 -7
  138. package/scripts/epic/epic-solo.ts +29 -28
  139. package/scripts/{git/git-epic-validate.ts → epic/epic-validate.ts} +13 -13
  140. package/{scripts-ai → scripts/epic}/epic.ts +17 -16
  141. package/scripts/gh/fix-gh-packages.ts +2 -1
  142. package/scripts/gh/gh-spawn.ts +12 -10
  143. package/scripts/git/constants.ts +1 -1
  144. package/scripts/git/git-branch.ts +10 -1
  145. package/scripts/git/git-command.ts +2 -2
  146. package/scripts/git/git-error.ts +2 -5
  147. package/scripts/git/git-execa-error.ts +6 -1
  148. package/{scripts-ai → scripts/git}/git-followup-finish.ts +7 -7
  149. package/scripts/git/git-followup-flush.ts +74 -48
  150. package/scripts/git/git-followup-issue-close.ts +2 -2
  151. package/scripts/git/git-followup-label.ts +1 -1
  152. package/scripts/git/git-followup-pending.ts +1 -1
  153. package/{scripts-ai → scripts/git}/git-followup-workflow.ts +23 -11
  154. package/scripts/git/git-gh-exec.ts +85 -26
  155. package/scripts/git/git-gh-issue-read.ts +2 -2
  156. package/scripts/git/git-gh-issue-rest.ts +2 -2
  157. package/scripts/git/git-gh-issue-write.ts +6 -6
  158. package/scripts/git/git-gh-pr-read.ts +0 -21
  159. package/scripts/git/git-gh-pr.ts +2 -23
  160. package/scripts/git/git-next-issues.ts +34 -5
  161. package/scripts/git/git-pr-followup-wrapup.ts +2 -6
  162. package/scripts/git/git-preflight.ts +25 -10
  163. package/scripts/git/git-push-transport.ts +12 -69
  164. package/scripts/git/git-spawn.ts +79 -3
  165. package/scripts/git/git-ssh-keepalive.ts +74 -0
  166. package/scripts/git/git-staging.ts +21 -9
  167. package/{scripts-ai → scripts/git}/git-workflow.ts +11 -11
  168. package/scripts/git/github-issue-url.ts +1 -1
  169. package/scripts/git/gone-branch.ts +3 -2
  170. package/scripts/git/issue-labels.ts +13 -1
  171. package/scripts/git/issue-rank.ts +89 -0
  172. package/scripts/git/issue-reference.ts +19 -0
  173. package/scripts/git/main-merge.ts +2 -1
  174. package/scripts/git/main-sync.ts +3 -2
  175. package/scripts/git/schemas.ts +1 -1
  176. package/scripts/git/stash-pop-args.ts +7 -13
  177. package/scripts/git/stash-pop-cli.ts +2 -1
  178. package/{scripts-ai → scripts/git}/telegram-test-logic.ts +2 -2
  179. package/{scripts-ai → scripts/git}/telegram-test.ts +7 -7
  180. package/scripts/hooks/format-edited-cli.ts +15 -0
  181. package/scripts/hooks/format-edited-file.ts +2 -9
  182. package/scripts/hooks/format-rewrite-notice.ts +2 -8
  183. package/scripts/hooks/pretool-guard-cli.ts +21 -0
  184. package/scripts/hooks/pretool-guard.ts +14 -15
  185. package/scripts/init/init-ai-copy.ts +2 -5
  186. package/scripts/init/init.ts +8 -4
  187. package/scripts/init/start-exec.ts +7 -1
  188. package/scripts/init/start-plan.ts +18 -5
  189. package/scripts/init/start-setup-pr.ts +46 -19
  190. package/scripts/init/start-steps.ts +43 -10
  191. package/scripts/init/start.ts +42 -11
  192. package/scripts/issue/issue-cite.ts +19 -1
  193. package/scripts/issue/issue-comment-cli.ts +2 -1
  194. package/scripts/issue/issue-file-cli.ts +2 -1
  195. package/scripts/issue/issue-fold-cli.ts +9 -16
  196. package/scripts/issue/issue-scout-cli.ts +8 -13
  197. package/scripts/issue/measure-rerun-cli.ts +7 -6
  198. package/scripts/josh/josh-command-map.ts +0 -102
  199. package/scripts/josh/josh-commands-ai.ts +2 -2
  200. package/scripts/josh/josh-commands-backlog.ts +1 -1
  201. package/scripts/josh/josh-commands-development.ts +3 -3
  202. package/scripts/josh/josh-commands-project.ts +1 -1
  203. package/scripts/josh/josh-commands-workflow.ts +4 -4
  204. package/scripts/lane/lane-child-marker.ts +16 -2
  205. package/scripts/lane/lane-cli.ts +34 -15
  206. package/scripts/lane/lane-open.ts +3 -2
  207. package/scripts/lane/lane-registry.ts +3 -6
  208. package/scripts/lane/lane-report.ts +10 -4
  209. package/scripts/lib/cli-flags.ts +20 -2
  210. package/scripts/lib/error-message.ts +9 -0
  211. package/scripts/lib/read-file.ts +26 -2
  212. package/scripts/observations/observation-ledger-home.ts +98 -26
  213. package/scripts/observations/observation-ledger-migrate.ts +26 -21
  214. package/scripts/observations/observation-ledger-prepare.ts +10 -20
  215. package/scripts/observations/observation-ledger.ts +58 -25
  216. package/scripts/observations/observations-flush-cli.ts +6 -23
  217. package/scripts/observations/observations-flush-landing.ts +2 -1
  218. package/scripts/observations/observations-flush.ts +29 -20
  219. package/scripts/package/package-scout-cli.ts +8 -16
  220. package/scripts/ports/port-command.ts +2 -1
  221. package/scripts/propagate/propagate-plan.ts +185 -0
  222. package/scripts/propagate/propagate-publish.ts +6 -7
  223. package/scripts/propagate/propagate-run.ts +5 -1
  224. package/scripts/propagate/propagate-steps.ts +18 -2
  225. package/scripts/propagate/propagate-targets.ts +13 -2
  226. package/scripts/propagate/propagate.ts +63 -44
  227. package/scripts/refactor/import-graph.ts +2 -6
  228. package/scripts/registry-migration/migrate-logic.ts +1 -0
  229. package/scripts/registry-migration/migrate.ts +3 -2
  230. package/scripts/registry-migration/user-npmrc.ts +2 -2
  231. package/scripts/release/github-release.ts +1 -1
  232. package/scripts/release/release-cli.ts +2 -1
  233. package/scripts/repo/repo-setting.ts +10 -8
  234. package/scripts/review/review-attest.ts +44 -0
  235. package/scripts/review/review-brief-cli.ts +49 -2
  236. package/scripts/review/review-brief.ts +46 -1
  237. package/scripts/review/review-finding-ledger.ts +3 -3
  238. package/scripts/review/review-findings-cli.ts +4 -11
  239. package/scripts/review/review-record-cli.ts +14 -11
  240. package/scripts/review/review-record.ts +6 -16
  241. package/scripts/review/review-stamps.ts +7 -0
  242. package/scripts/rules/decision-oracle.ts +2 -2
  243. package/scripts/rules/implementation-cut.ts +1 -1
  244. package/scripts/rules/issue-fold.ts +1 -2
  245. package/scripts/rules/lane-carry-conflict.ts +1 -2
  246. package/scripts/rules/lane-park.ts +1 -2
  247. package/scripts/rules/pre-gate-cut.ts +2 -2
  248. package/scripts/rules/rule-body-guard.ts +2 -2
  249. package/scripts/rules/rule-value-cache.ts +99 -0
  250. package/scripts/rules/rule-value-cli.ts +10 -9
  251. package/scripts/rules/rule-value.ts +1 -1
  252. package/scripts/run/run-carry-args.ts +2 -6
  253. package/scripts/run/run-carry-cli.ts +5 -7
  254. package/scripts/run/run-cut-args.ts +7 -13
  255. package/scripts/run/run-ending-cli.ts +4 -7
  256. package/scripts/run/run-event-stream.ts +2 -5
  257. package/scripts/run/run-headless.ts +22 -6
  258. package/scripts/run/run-liveness-cli.ts +4 -7
  259. package/scripts/run/run-parent-cut-hook.ts +144 -0
  260. package/scripts/run/run-progress-args.ts +2 -6
  261. package/scripts/run/run-progress-cli.ts +2 -1
  262. package/scripts/run/run-progress-read.ts +2 -1
  263. package/scripts/run/run-progress.ts +21 -8
  264. package/scripts/run/run-ship-cli.ts +6 -74
  265. package/scripts/run/run-ship-preflight.ts +87 -0
  266. package/scripts/run/run-ship-review-steps.ts +5 -26
  267. package/scripts/run/run-ship-review.ts +9 -0
  268. package/scripts/run/run-ship-scoped.ts +44 -0
  269. package/scripts/run/run-ship-stage.ts +5 -1
  270. package/scripts/run/run-ship-steps.ts +105 -0
  271. package/scripts/run/run-ship.ts +2 -0
  272. package/scripts/run/run-tail-cli.ts +3 -3
  273. package/scripts/run/run-tidy-stashes.ts +7 -14
  274. package/scripts/run/run-wake-cli.ts +4 -8
  275. package/scripts/run/run-wake-describe.ts +19 -1
  276. package/scripts/run/run-wake-driver.ts +15 -2
  277. package/scripts/run/run-wake-session.ts +14 -4
  278. package/scripts/run/run-watcher-hook.ts +1 -1
  279. package/scripts/safe-chain/project-config.ts +3 -6
  280. package/scripts/security/security-audit-provision.ts +6 -7
  281. package/scripts/sonar/sonar-hotspots-cli.ts +2 -1
  282. package/scripts/sync/directory-copy-guard.ts +2 -1
  283. package/scripts/sync/sync-ai-files.ts +3 -3
  284. package/scripts/sync/template-source-logic.ts +3 -4
  285. package/scripts/test/e2e-retry-check.ts +3 -6
  286. package/scripts/time-runtime/time-bundle-call.ts +2 -2
  287. package/scripts/ui/ui-routes-cli.ts +3 -6
  288. package/scripts/version/bump-version.ts +2 -1
  289. package/scripts/version/npm-registry.ts +97 -0
  290. package/scripts/version/version-commands.ts +5 -4
  291. package/scripts/version/version-remote.ts +38 -33
  292. package/scripts/version/version-targets.ts +3 -3
  293. package/.claude/skills/workflow-commands/rule-residency.md +0 -267
  294. package/evals/scenarios/consult-not-execute.json +0 -20
  295. package/evals/scenarios/no-implicit-workflow.json +0 -26
  296. package/evals/scenarios/overrides-both-locations.json +0 -29
  297. package/evals/scenarios/upstream-interrupt.json +0 -23
  298. package/evals/scenarios/workflow-skill-loaded.json +0 -16
  299. package/prompts/agent-lint-protocol.json +0 -79
  300. package/prompts/agent-rules.md +0 -63
  301. package/prompts/collaboration-workflow/consultation-vs-execution.md +0 -8
  302. package/prompts/collaboration-workflow/distributed-docs.md +0 -7
  303. package/prompts/collaboration-workflow/durable-rules.md +0 -24
  304. package/prompts/collaboration-workflow/latest-first.md +0 -14
  305. package/prompts/collaboration-workflow/no-clones.md +0 -11
  306. package/prompts/collaboration-workflow/simplicity-first.md +0 -9
  307. package/prompts/collaboration-workflow/single-source-rules.md +0 -13
  308. package/scripts/build/shim-shell.ts +0 -25
  309. package/scripts/claude/skill-meta.ts +0 -37
  310. package/scripts/document/document-scan.ts +0 -108
  311. package/scripts/document/generate-catalog.ts +0 -69
  312. package/scripts/document/retired-phrases.ts +0 -143
  313. package/scripts/document/review-agent-type.ts +0 -46
  314. package/scripts/document/single-source.ts +0 -73
  315. package/scripts/git/git-fixture-workspace.ts +0 -88
  316. package/scripts/hooks/format-edited-file-fixtures.ts +0 -109
  317. package/scripts/hooks/prompt-hooks.ts +0 -38
  318. package/scripts/init/hook-command-bootstrap.ts +0 -83
  319. package/scripts/issue/issue-logic.ts +0 -50
  320. package/scripts/josh/__snapshots__/josh-command-map.test.ts.snap +0 -1227
  321. package/scripts/josh/josh-script-reader.ts +0 -11
  322. package/scripts/package/production-dependency-graph.ts +0 -68
  323. package/scripts/retrospective/retrospective-cli.ts +0 -97
  324. package/scripts/retrospective/retrospective.ts +0 -127
  325. package/scripts/rules/delivered-rules-harness.ts +0 -72
  326. package/scripts/rules/top-level-scripts-guard.ts +0 -47
  327. package/scripts/run/run-carry-flush.ts +0 -58
  328. package/scripts/run/run-transcript.golden.txt +0 -57
  329. package/scripts/run/run-wake-work.ts +0 -108
  330. package/scripts/sync/dependabot-pin-logic.ts +0 -135
  331. package/scripts/test/classify-isolation.ts +0 -149
  332. package/scripts/test/http-fault-injection.ts +0 -79
  333. package/scripts/test/josh-harness-environment.ts +0 -260
  334. package/scripts/test/josh-harness.ts +0 -96
  335. package/scripts/test/pilot-files.ts +0 -452
  336. package/scripts/test/pilot-measure.ts +0 -78
  337. package/scripts/test/test-network-guard.ts +0 -453
  338. package/scripts/test/test-repository-guard.ts +0 -317
  339. package/scripts/test/test-state-guard.ts +0 -85
  340. package/scripts/test/test-stdout-guard.ts +0 -54
  341. package/scripts/test/test-telegram-guard.ts +0 -90
  342. package/scripts/test/unit-guard-environment.ts +0 -12
  343. package/scripts/test/unit-projects.ts +0 -139
  344. package/scripts/test/vitest-include-globs.ts +0 -12
  345. package/scripts/time-runtime/time-batch-guard-fixtures.ts +0 -66
  346. package/scripts-ai/completion-gate.ts +0 -13
  347. package/scripts-ai/environment-loader.ts +0 -9
  348. /package/{scripts-ai → scripts/epic}/epic-cli-argv.ts +0 -0
  349. /package/{scripts-ai → scripts/epic}/epic-cli-remove.ts +0 -0
  350. /package/{scripts-ai → scripts/git}/followup-issue-number.ts +0 -0
@@ -1,109 +1,5 @@
1
1
  ## 後から関連が判明した Issue を epic に束ねる
2
2
 
3
- 「2 件以上に分割したら常に epic を作る」は既に効いているが、**発火するのは 1 つの要望をその場で分割したときだけ**である。別々のタイミングで起票された Issue が後から関連していると分かっても、束ねる仕組みが無い。次が漏れる。
3
+ **この規則の単一ソースは `.claude/skills/epic-commands/SKILL.md` → "`josh epic:bundle <N>` — does this new issue belong with one already filed?" である。** 発火点、強い信号、候補探索の範囲、決定木、所属先の記録、順序の記録、起票前の `issue:scout` はすべてそこにある。レビュー上限で切り出す後追い Issue の起票と答えへの対応は `prompts/review.md` → "Three-way disposition after the cap" が単一ソースである。
4
4
 
5
- - 実装中に Tier A で起票した Issue が、既存の open Issue と順序や依存を持っていた場合
6
- - 何日か空けて起票した 2 件が、実は同じ作業の前後だった場合
7
- - 既存 Issue が実行順を必要としていることに、後から気づいた場合
8
-
9
- いずれも束ねられないまま個別に実行され、順序が守られず、分割の根拠がどこにも残らない。
10
-
11
- ### 発火点
12
-
13
- **Issue を新規に起票した直後**に、既存の open Issue を調べる。`kickoff` / `fullrun` / `halfrun` が起票したとき、および実装中に Tier A で起票したとき(`backlogrun` 実行中を含む)。
14
-
15
- `pnpm josh epic:bundle <N>`(エイリアス `eb`)が候補を探して推奨を表示する。起票は `pnpm josh issue:file` で行い、このコマンドが最終段として `epic:bundle` を実行して答えを表示するので、別に呼ぶのは `⚠` で再実行を案内されたときだけである。**このコマンドは何も書き込まない** — 候補を出すのが機械、束ねるかを決めるのは AI である。
16
-
17
- ### 起票の「前」に答えるのは `issue:scout`
18
-
19
- `pnpm josh issue:scout "<title>"`(エイリアス `isc`)は、まだ存在しない Issue について同じ配属先の問いに答える(joshuafolkken/kit#1252)。**配属の判定は `epic:bundle` のものをそのまま呼んでおり、実装は 1 つしかない。** 加えて、`epic:bundle` が意図的に採らないシグナル — タイトルの語の重なりによる**重複候補** — を返す。既存 Issue の束ね直しに似た見出しが立つのは強シグナルだけで十分だからだが、「もう起票されていないか」は起票前にしか意味を持たない別の問いであり、しきい値を混ぜていない。
20
-
21
- **両方を実行する。順番が違うだけである。** どちらも `pnpm josh issue:file` が 1 回の呼び出しの中で実行する。
22
-
23
- | いつ | コマンド | 何について答えるか |
24
- | -------------- | ----------------------- | -------------------------------------------------- |
25
- | 起票の**前** | `issue:scout "<title>"` | まだ番号を持たない下書き。タイトルと本文がある |
26
- | 起票の**直後** | `epic:bundle <N>` | 実在する Issue。番号と、それに記録された関係がある |
27
-
28
- 手順上の位置づけと、重複候補が見つかったときに起票せず止まる規則は `.claude/skills/workflow-commands/SKILL.md` → §2e が単一ソースである。
29
-
30
- ### 後追い Issue は起票した直後に EPIC へ束ね直す
31
-
32
- レビュー上限(`prompts/review.md` → "Review round cap")で切り出す後追い Issue は、**このワークフローで最も件数の多い起票経路**である。それでも手順は長らく「起票して現在の Issue を参照する」までしか定めておらず、束ね直しへの導線が無かった。手順どおりに読むと起票して次へ進んで終わる。
33
-
34
- なお 2 巡目を終えた残指摘は、いまは**3 分岐(その場で直す/起票する/PR に 1 行残して落とす)**に振り分ける(`prompts/review.md` → "Review round cap")。本節が扱うのは**起票する**分岐に入ったものだけであり、その場で直したものと落としたものは Issue にならないので束ね直しの対象にもならない。
35
-
36
- **既定は「PR に 1 行残して落とす」側であり、起票する分岐は runtime path に届く確定バグに限る**(joshuafolkken/kit#1469)。この経路はバックログ純増の 3 つの製造元のうち最も件数が多かったため、既定を落とす側へ置き直した。したがって本節が発火する回数自体が以前より少ない — それは手順の省略ではなく、既定が変わった結果である。単一ソースは `prompts/review.md` → "Three-way disposition after the cap"。
37
-
38
- 手順は 3 段であり、**上の発火点の一適用ではなく、後追い起票の手順そのものに書く**。別の文書を読みに行く前提にしない。
39
-
40
- **3 段は CI 待ちの中で実行する。コミットの前ではない。** PR を開くフロー(`fullrun` / `backlogrun`)では `pnpm josh git -y` の後・`pnpm josh followup` の前に置く。PR を開かないフロー(`halfrun`、ワークフロー外のコミット前セルフレビュー)では、隠れる先の CI が無いので振り分けが決まった時点で実行する。**期限は変わらない** — 現在の Issue が閉じるのはマージ時点であり、マージするのは `followup` なので、どの段も親が open のうちに終わる。第 2 段が要求しているのはそれだけである。変わるのは秒が誰のものかだけで、実測では `epic:bundle` 43 秒・`epic --add` 18 秒(joshuafolkken/kit#1229)に対し、joshuafolkken/kit#1238 の `followup` は 122 秒のうち 78 秒を CI の完了待ちに費やしている(joshuafolkken/kit#1239)。
41
-
42
- **これは「レビューを CI と並走させる」ではない。**(ここで言うレビューは 1 周目のことであり、2 周目については下の段落で別に扱う。) joshuafolkken/kit#1216 の (b) は不採用と決定済みであり、却下の理由は規則ではなく仕組みである — あちらは**コードを変える作業**を CI と重ねるため、修正を push するたびに CI がやり直しになり、重ねた分をそのまま払い戻す。起票はコードを 1 行も変えないので、走っている CI がそのまま使える。**1 周目のレビュー**はコミットの前のままで、「コミット前セルフレビュー」は書き換えていない。**2 周目だけは CI と並走する**(joshuafolkken/kit#1261)— 同じ仕組みを逆から読んだ結果であり、2 周目は fix delta しか読まず、通常はコードを 1 行も変えない。変えた場合は同一ブランチへの追加コミット 1 つと CI のやり直し 1 回を払う。単一ソースは `.claude/skills/workflow-commands/chain-rule.md` → "The pull request opens between the rounds, so CI runs beside round 2"。
43
-
44
- 1. 残指摘を後追い Issue として起票し、現在の Issue を参照する。起票は `pnpm josh issue:file "<title>" --body-file <本文ファイル> --depth <n> --route review-cap` で行う
45
- 2. **現在の Issue が閉じる前に**起票する。`issue:file` が新規 Issue について `epic:bundle` を実行する。候補探索は open Issue しか読まないため、親が閉じた後では恒久的に `none` になる(joshuafolkken/kit#947)
46
- 3. 答えに従う。**`epic:bundle` は推奨するだけで何も書き込まない**ので、「実行する」とは書き込みコマンドを自分で打つことである。**epic 本文の手編集は禁止** — タスクリストと `blocked-by` が食い違い、`epic:next` が `error` を返す
47
-
48
- | 答え | すること | Tier |
49
- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------------- |
50
- | `add_to_epic` | `pnpm josh epic --add <E> <新規>`(順序があるなら `--before <M>` / `--after <M>`) | **A — 確認不要** |
51
- | `create_epic` | `pnpm josh epic "<title>" <新規> <相手> [--ordered]` | **A — 確認不要** |
52
- | `ask`(候補が複数の EPIC に散っている) | **推奨する epic を自分で選び、書き込みコマンドを実行し、採用・却下・理由・決定日を新規 Issue とその epic の `## Decisions` の両方に記録する。停止もせず park もしない**(joshuafolkken/kit#1339)。2 つの epic が本当に甲乙つけがたいときだけ止める | **A — 確認不要** |
53
- | `none` | 何もしない | — |
54
- | **`Could not confirm which epic already tracks these — do not place this issue in one.`** — epic 一覧が打ち切られていたときの答えで、**Issue を epic に入れる 3 つの答え(`add_to_epic` / `create_epic` / `ask`)すべてに代わって出る**。いずれも「この Issue をまだどの epic も追跡していない」を前提にしており、打ち切られた一覧ではそれを確かめられない。子と宣言順は**意図的に出ない**(それはこの行がするなと言っている配属のレシピそのものだから)(joshuafolkken/kit#1697) | **epic に入れない。** 一覧を最後まで読める状態にしてから訊き直すか、何と言ったかを添えて停止・報告する。`Already in an epic`(追跡している epic を実際に読めた答え)は打ち切りがあっても有効なままである | — |
55
- | **コマンドが答えられなかった** — 非ゼロ終了、または `Nothing to bundle.` の上に出た**あらゆる** ⚠ 警告(一覧の打ち切り、関係を読めなかった Issue)。記録済みの依存は 2 つある強い信号の片方なので、関係の読み取り失敗は本来の `add_to_epic` を `none` に化けさせる。断定的な答え(`Already in an epic` / `Add it to the epic …`)は警告が併記されていても有効である | 何と言ったかを添えて停止・報告する。**警告の後の `none` は「束ねる相手が無い」ではない** — 探索が不完全なのであり、答えとして読むと本規則が塞ごうとしている経路そのもので Issue が EPIC 無しになる(joshuafolkken/kit#950) | — |
56
-
57
- **`none` は正当な答えである。** コミット前セルフレビューをワークフローの外で回した場合、現在の Issue が存在せず参照先が無いため候補は出ない。そのときは束ねずにバックログへ残す — 手順が求めるのは「コマンドを実行して答えに従うこと」であって、必ず EPIC に入れることではない。
58
-
59
- **逆に、実行せずに起票だけで終えると、指摘は落ちるのではなく永久に park される。** `epic:next` が返すのは EPIC のタスクリストにある子だけなので、どの EPIC にも属さない Issue は実行中の `backlogrun` に一度も渡らない(拾うには番号を知っている人が要る)。バックログから見れば「落ちた」のと区別が付かない。
60
-
61
- 実測である。joshuafolkken/kit#943 は 2 回目のレビューから切り出され、本文に `親: joshuafolkken/kit#891` と明記していながら、どの EPIC の子にもなっていなかった。親 #891 が閉じたのはその 3 分後である。同じ経路でも手順が実行された joshuafolkken/kit#911 では `epic:bundle` が EPIC を名指しし、そのまま追加されている。**差は、コマンドを打ったかどうかだけだった**(joshuafolkken/kit#946)。
62
-
63
- なお **#943 の取りこぼしには 2 層目の原因もある** — 起票が親の close より後になると、`epic:bundle` の候補探索が open Issue しか読まないため恒久的に `Nothing to bundle.` を返す。そちらは joshuafolkken/kit#947 が扱う。本節が直すのは「手順が守られなかった」側だけである。
64
-
65
- ### 強い信号だけを根拠にする
66
-
67
- - 本文の相互参照(新規 Issue が既存を参照している、または既存が新規を参照している)
68
- - 既存の `blocked-by` 関係
69
-
70
- **タイトル・本文の内容的な類似は、それだけでは束ねる根拠にしない。** 「関連している」は際限なく広がるため、閾値を持たないと無関係な Issue まで巻き込む。類似は AI の判断を補強する材料に留める。
71
-
72
- **候補探索は open backlog に限らない。** 対象 Issue の本文が名指ししている番号は、状態を問わず 1 件ずつ読む。open 限定のままだと、後追い Issue が起票されてから親が close するまでの数分間しか正しく答えられない(joshuafolkken/kit#943 では約 3 分。過ぎると `Nothing to bundle.` を exit 0 で返し、「読めなかった」ではなく「無かった」と断定していた)。
73
-
74
- - **closed の参照先は、open な EPIC が既に追跡している場合にのみ候補にする。** 回収したい答えは `add_to_epic` である。閉じた Issue を子に持つ新規 EPIC は実行するものが残っていない
75
- - **open の参照先は無条件に候補にする。** 一覧に出てこなかったのは一覧が打ち切られたからであって、無関係だからではない
76
- - 追加読み取りは参照 1 件につき 1 リクエストで、件数に上限があり、関係の読み取りと同じ形でバッチ化される。**読み取りの失敗も、上限で読まなかった参照も、欠落として報告し「強い信号なし」に畳み込まない** — 黙って打ち切る guard は、「見るのをやめた」を「関係が無かった」と言い換える元の欠陥そのものである
77
- - **番号が pull request だった場合は候補にしない。** REST の issue エンドポイントは PR にも答え、マージ済み PR の state は `CLOSED` ではないため、この判定が無いと「修正は #952 で入った」という散文が PR を新規 EPIC の子に混ぜる
78
- - **実在しない番号は欠落として報告しない。** 打ち間違いや他リポジトリの番号のように GitHub が何にも解決できない参照は、候補にも欠落にも入れず黙って捨てる。これを欠落として報告すると、散文中の `#N` が 1 つ狂っただけで `⚠ Could not read #N.` が verdict の上に出て、上の「打ち切り警告の後の `Nothing to bundle.` は答えではない」規則により**無人実行が停止する** — 存在したことのない参照のために人を呼ぶことになる(joshuafolkken/kit#957)
79
- - **その判別は `gh` のエラー文言ではなく HTTP ステータスコードで行う。** 実在しない番号は REST で **404**、レート制限は **403 / 429** である。GitHub は権限の無い Issue にも存在を漏らさないため 403 ではなく 404 を返すので両者はステータスからは原理的に区別できないが、このコマンドは **直前に open 一覧を取得したのと同じリポジトリ**を叩くため、そこで見えない番号は存在しない番号である。`gh api` の失敗はステータスコードではなく stderr の文言として届くため、**読み取りが失敗したときにだけ** REST を 1 回叩いて分類する。成功経路と、この区別を必要としない呼び出し元には追加リクエストは発生しない — バックログの関係読み取りは最大 200 件あり、レート制限で全滅したときにさらに 200 リクエストを撃つことになるためである。分類する経路は参照の上限(20 件)で抑えられている
80
- - 追うのは対象 Issue 自身の本文だけである。逆方向(閉じた Issue が対象を名指しする)は closed 全件走査になり、かつ不要である — 後追い Issue が親を名指しするのは起票手順そのものだからである
81
-
82
- 候補探索の解析は `josh epic:audit` の「暗黙の依存」検査と**同一の実装を共有する**。あちらは epic 内に閉じた解析、こちらはバックログ全体への適用というだけで、読む対象は同じ「本文中の Issue 参照」である。同じ解析を 2 回書かない。
83
-
84
- ### 決定木(「常に新規 epic を作る」ではない)
85
-
86
- Issue は 1 つの epic にしか属せない(タスクリストで追跡されるため)。したがって分岐が要る。
87
-
88
- | 状況 | 動作 | Tier |
89
- | -------------------------------------------------------------------- | -------------------------------------------------------------------------------------- | ---- |
90
- | **新規 Issue 自身が既に epic の子** | 何もしない。Issue は 1 つの epic にしか属せず、epic 間の移動はこのルールの担当ではない | — |
91
- | 関連候補が**既に epic の子** | **その epic に追加**する(新規 epic を作らない) | A |
92
- | 候補が **epic とその親 epic** に分かれている | **内側(子)の epic に追加**する。親は既に子を含んでいる | A |
93
- | 候補が**複数の異なる epic** に散っている | **推奨する epic を選んで追加し、理由を記録する** | A |
94
- | どの epic にも属さない候補があり、新規 Issue と合わせて **2 件以上** | **新規 epic を作って束ねる** | A |
95
- | 強い信号を持つ候補が無い | 何もしない | — |
96
-
97
- 束ねるのは可逆(epic は編集でき、子は外せる)なので Tier A で確認を挟まない。**所属先の選択も同じく Tier A である** — `epic --add` 1 回で別の epic に移せるため、候補が複数の epic に散っていても止まらず、推奨する 1 つを選んで理由を記録する(joshuafolkken/kit#1339)。
98
-
99
- **所属先を選ぶことは epic の統合ではない。** epic 同士の統合は誰も提案していない別の操作であり、本当に必要なら**そのときに**改めて人に聞けばよい。**記録が自律の対価である** — 採用・却下・理由・決定日を残さない自動決定は、後から誰も辿れない決定を下しただけになる。
100
-
101
- **入れ子の親子関係では、この答えはもう出ない**(joshuafolkken/kit#1079)。親 epic は既に子 epic を含んでいるので、両者は選ぶべき対等な 2 択ではない。したがって関与する epic のうち**他の関与 epic の祖先にあたるものを落とし**、内側の 1 件が残ればそこへ追加する。この誤検出は 3 件記録されており、うち 1 件は実装が完了しレビューも収束し PR も mergeable だった Issue のバッチを丸ごと止めた。**落とすのは親だけで、対等な epic は落とさない** — 入れ子の連鎖の横に無関係な epic が 1 つあれば依然として尋ねるし、親子宣言が循環していて内側が定まらない場合も絞り込まずに尋ねる。
102
-
103
- ### 束ねたら順序も記録する
104
-
105
- 関連が順序を含む場合、`blocked-by` を付与し、epic 本文の `Dependencies` にも矢印記法で書く。既存 epic への追加時も同じ。**順序を記録しないと、束ねた事実だけが残って束ねた理由が消える。** ただし**誰も宣言していない順序をここで捏造しない** — 既に宣言されている関係だけを引き継ぐ。
106
-
107
- ### 規模
108
-
109
- 実測で open Issue は十数件であり、全件を舐めても一瞬なので**索引やキャッシュは用意しない**。件数が問題になってから考える。
5
+ 経緯(joshuafolkken/kit#943 / #946 / #947 の取りこぼし、CI 待ちに起票を置く根拠の計測)は [`docs/maintainers/epic-commands-rationale.md`](../../docs/maintainers/epic-commands-rationale.md) にある。
@@ -2,6 +2,8 @@
2
2
 
3
3
  `CLAUDE.md` →「Never carry a file's new text inside a shell command.」の正典。
4
4
 
5
+ `pnpm josh rule:guard`(file-body の行)が、既存ファイルを書き戻すヒアドキュメント・書き込みを伴うインタプリタ heredoc / `node -e`・in-place `perl -0pi -e` をその呼び出しで拒否し、規則を述べる。**このファイルが担うのはガードに見えないもの**である — Bash を通らない Edit / Write の全文書き直し、ガードを素通りする `sed -i` の 4 条件、そしてコストである。
6
+
5
7
  ### 何を禁じているか
6
8
 
7
9
  **編集後のテキストを丸ごとコマンド行に載せる形を禁じる。** 典型は、インタプリタを起動して領域を書き戻す次の形である。
@@ -40,14 +42,7 @@ PY
40
42
 
41
43
  **レビュー指摘の修正がこの規則の主戦場である。** 「この行の条件が逆」「この定数を切り出す」といった局所的な指摘ほど、部分編集は小さくなる。一方で全文書き直しのコストはファイルの大きさで決まり、指摘の小ささでは下がらない。**指摘が局所的であるほど、全文書き直しとの差は開く。**
42
44
 
43
- joshuafolkken/kit#1251 のランで実測した値(joshuafolkken/kit#1260):
44
-
45
- | ターン | 出力トークン | 内容 |
46
- | ------------------ | ------------ | -------------------------------------------------------- |
47
- | レビュー指摘の修正 | 11,104 | 2 ファイルの全文書き直し。そのランの単一ターンとして最大 |
48
- | 同じランの別ターン | 3,282 | 全文書き直し |
49
-
50
- 実効生成速度は約 87 トークン/秒なので、**この 1 ランで約 2 分 45 秒が、すでに存在する行を打ち直すことに使われている。**
45
+ 実測では 1 ランで約 2 分 45 秒が、すでに存在する行を打ち直すことに使われていた(joshuafolkken/kit#1260)。内訳は `docs/maintainers/file-edits-rationale.md` → "全文書き直しの実測"。
51
46
 
52
47
  ### `sed -i` を使う前に満たす 4 条件
53
48
 
@@ -71,54 +66,12 @@ joshuafolkken/kit#1251 のランで実測した値(joshuafolkken/kit#1260):
71
66
 
72
67
  ### なぜコストが二重になるか
73
68
 
74
- インタプリタで書き戻す形は、編集後の本文が**コマンド本文とファイルの両方**に載る。さらに悪いのは持続性である。**コマンド本文は、書いた時点以降のすべてのリクエストで読み直される。** ランの序盤に書いた編集スクリプトほど、そのランの残り全リクエストぶん課金され続ける。ファイル側は次に読んだときだけ載るのに対し、コマンド側は消えない。
75
-
76
- joshuafolkken/kit#1144 のランのトランスクリプトで実測した内訳(joshuafolkken/kit#1150):
77
-
78
- | 種別 | 割合 |
79
- | ----------------------- | --------- |
80
- | tool_result | 37.7% |
81
- | **Bash のコマンド本文** | **30.2%** |
82
- | thinking | 24.9% |
83
- | text | 4.7% |
84
-
85
- Bash コマンド本文 97,042 tok・427 呼び出しの内訳:
86
-
87
- | 種別 | 呼び出し数 | トークン | 割合 |
88
- | ------------------------------------- | ---------- | ---------- | --------- |
89
- | `python3 - <<'PY'` 形式のファイル編集 | 145 | **79,317** | **81.7%** |
90
- | git / gh / pnpm | 140 | 12,716 | 13.1% |
91
- | 読み取り・検索 | 110 | 3,215 | 3.3% |
92
- | その他 | 32 | 1,794 | 1.8% |
93
-
94
- **編集スクリプトだけでセッション全体のコンテキストの約 2 割を占めていた。** 1 回あたり平均 547 tok、上位は 1,200〜1,800 tok。総量そのものより、二重計上と持続が効いている。
95
-
96
- 適用後の再計測は joshuafolkken/kit#1159 が担当する。
69
+ インタプリタで書き戻す形は、編集後の本文が**コマンド本文とファイルの両方**に載る。さらに悪いのは持続性である。**コマンド本文は、書いた時点以降のすべてのリクエストで読み直される。** ランの序盤に書いた編集スクリプトほど、そのランの残り全リクエストぶん課金され続ける。ファイル側は次に読んだときだけ載るのに対し、コマンド側は消えない。実測の内訳は `docs/maintainers/file-edits-rationale.md` → "コマンド本文の実測内訳"。
97
70
 
98
71
  ### なぜ resident に置くか
99
72
 
100
- residency 基準(`residency.md`)は 1 問で決まる。
101
-
102
- > **その規則は、skill がロードされていないターンでも効く必要があるか。**
103
-
104
- 答えは yes である。ファイル編集はワークフローのキーワードが打たれていないターンでも起き、**編集の直前にロードされる skill は存在しない。** skill 側に本体を置いた場合、この規則は一度も発火しない — 規則を書いたのに削除したのと同じ振る舞いになる。
105
-
106
- そのうえで、常駐側に置くのは**トリガと導線だけ**である。常駐側に残すのは次の 3 点で、それだけで正しく振る舞える。
107
-
108
- 1. 領域を指定する編集は Edit で行い、インタプリタや heredoc で領域を書き戻さない
109
- 2. **Edit 自体を全文へ広げない**(joshuafolkken/kit#1260)
110
- 3. 判断基準は「本文を丸ごと運ぶか」であってツール名ではない(短い `sed -i` は許される)
111
-
112
- 実測値・可否表・二重計上の説明・全文書き直しが許される 3 条件、そして**インタプリタの具体形**(`python3 - <<'PY'` / `node -e` / `cat > file <<'EOF'`)はこのファイルにあり、常駐側からは落としている。これらは「読まなくても正しく振る舞えるが、読めばより納得できる」種類の記述だからである。**具体形を指し先へ移したのは削除ではなく移動である** — 禁止の区分は常駐側の「インタプリタや heredoc」が担い、個々の形はこのファイルの可否表が担う。
73
+ 根拠は `docs/maintainers/file-edits-rationale.md` → "なぜ resident に置くか"。
113
74
 
114
75
  ### マーカーテスト
115
76
 
116
- `scripts/document/document-markers.test.ts` が次を固定する。
117
-
118
- - `CLAUDE.md` に規則のトリガ文と判断基準の一文が resident で存在すること
119
- - `CLAUDE.md` に全文書き直しの禁止(「Edit を全文へ広げない」)が resident で存在すること
120
- - 常駐側がこのファイルを導線として指していること
121
- - このファイルが判断基準・可否表・`sed -i` の 4 条件・全文書き直しの 3 条件を持っていること
122
- - インタプリタの具体形 3 つ(`python3 - <<'PY'` / `node -e` / `cat > file <<'EOF'`)が常駐側にも residency 一覧にも残っておらず、このファイルにあること
123
- - 実測値(79,317 / 81.7% / 30.2% / 11,104 / 3,282)が常駐側にも residency 一覧にも貼り戻されていないこと
124
- - residency の一覧(`.claude/skills/workflow-commands/SKILL.md` とこのディレクトリの `residency.md`)にこの規則が載っていること
77
+ 固定している内容は `docs/maintainers/file-edits-rationale.md` → "マーカーテスト"。
@@ -76,7 +76,7 @@ Issue には次の要素を必ず含める。
76
76
  - **互換性を壊す変更は影響を本文で宣言する。** 既存の利用者、API、設定の契約を変える場合は、`## 背景` の直下に `- 互換性: 破壊的変更` を書き、廃止対象と影響を説明する。移行措置や事前案内があっても破壊的変更なら宣言する。この宣言があれば `pnpm josh issue:file` が `breaking-change` ラベルを同じ作成リクエストに付ける。互換性を保つ変更には付けない。影響が曖昧なら起票文案で対象の利用者と契約を明確にしてから分類する
77
77
  - **本文が宣言する分類ラベルは `pnpm josh issue:file` がすべて起票時に付ける。** `bug`、`enhancement`、`breaking-change` は組み合わせて付くことがある。`depth`・`route` などのラベルと併せて 1 回の作成リクエストで付け、宣言が無いとき(`issue:lint` の `labels: none`)は分類ラベルを付けない。Issue が `enhancement` と `breaking-change` の両方を持つとき、PR のリリース分類は `breaking-change` 一つにする。Issue の目的の分類と PR のリリース分類を区別する
78
78
  - **`## 発火点`** には、その規則が破れる瞬間に最初に呼ばれるツールコール名を 1 つ書く。名前は `prompts/collaboration-workflow/rule-delivery.md` の配送表に載る、フックで配送可能なツール(`Bash` / `Edit` / `Read` / `Write` / `AskUserQuestion`)と突き合わせる。**表に無い名前**(そもそもツールコール名でない)と**不一致**(既知のツールだが配送できない)は区別して印字され、joshuafolkken/kit#2201 の「規則は正しいが名指ししたコールが実際に破れるコールの 1 つ後ろ」を起票時に検出する
79
- - **`## ベースライン`** は **「コマンド + 値」** で書く。``- `<測定コマンド>` → <現在の値>`` の形に限り、自然文だけの測定説明は受け付けない(再実行できないため)。マージ後に `pnpm josh measure:rerun` が同じコマンドをやり直し、**before / after の対**を印字する。値が動かなかったとき、反証された前提として `docs/maintainers/observations.md` に 1 行追記される(既存の append-only 台帳を使い、別の台帳は作らない)
79
+ - **`## ベースライン`** は **「コマンド + 値」** で書く。``- `<測定コマンド>` → <現在の値>`` の形に限り、自然文だけの測定説明は受け付けない(再実行できないため)。マージ後に `pnpm josh measure:rerun` が同じコマンドをやり直し、**before / after の対**を印字する。値が動かなかったとき、反証された前提として `docs/maintainers/observations/` の、その時点のブランチが指す Issue のファイルに 1 行追記される(既存の append-only 台帳を使い、別の台帳は作らない)
80
80
  - **`## 再現`** は **「コマンド + 実際の出力」** で書く。コマンドを backtick、出力をフェンス(``` または ~~~)で囲む。自然文の「確認した」は再実行できないため受け付けない(`## ベースライン` と同じ理由)。読みだけの起票を起票時に弾くためである
81
81
  - **検査は `pnpm josh issue:lint <path>` が行う。** 対象判定・3 見出しの有無・発火点の配送可否・ベースラインが「コマンド + 値」か・再現が「コマンド + 実際の出力」かと、起票時に必要な分類ラベルを、起票前の本文ファイルからまとめて答える(`pnpm josh issue:file` は起票前に同じ検査を行い、問題があれば起票しない)
82
82
 
@@ -94,7 +94,7 @@ Issue には次の要素を必ず含める。
94
94
 
95
95
  - **見出しは固定する**。「書いた人が置いた場所」ではなく grep で機械的に見つかるようにするため。起票元 Issue 側は、その場で本文を書いている最中なら本文に、既に本文が確定しているなら同じ見出しでコメントに書く
96
96
  - **リンクは必ずリポジトリ修飾する**(`owner/repo#N` または完全 URL)。**裸の `#N` を使ってはならない** — 上流リポジトリ内では同番号の別 Issue に解決され、黙って誤ったものを指す
97
- - **チェックボックス行(`- [ ] owner/repo#N`)で書いてはならない。散文か素の箇条書き(`- owner/repo#N`)にする。** `scripts/git/git-epic-parse.ts` の `has_external_task_list_entry` は「チェックボックス付きで他リポジトリを参照する行」を検出すると epic の自動クローズを無効化する。これは**本物の他リポジトリ子 Issue に対しては正しい挙動**(その状態は別リポジトリを指定しないと読めないため)だが、単なる後方参照をその記法で書くと epic が永久に open のまま残る。判定はチェックボックスの有無だけを見るので、素の箇条書きは安全である
97
+ - **チェックボックス行(`- [ ] owner/repo#N`)で書いてはならない。散文か素の箇条書き(`- owner/repo#N`)にする。** `scripts/epic/epic-parse.ts` の `has_external_task_list_entry` は「チェックボックス付きで他リポジトリを参照する行」を検出すると epic の自動クローズを無効化する。これは**本物の他リポジトリ子 Issue に対しては正しい挙動**(その状態は別リポジトリを指定しないと読めないため)だが、単なる後方参照をその記法で書くと epic が永久に open のまま残る。判定はチェックボックスの有無だけを見るので、素の箇条書きは安全である
98
98
  - **未起票の候補には `## Upstream candidate` を使い、`## Upstream issues` を使わない**。後者は「既に起票した」ことを主張する見出しであり、third-party リポジトリへの報告はユーザーの明示指示があるまで起票しないため、両者は必ず別の見出しに置く(→「第三者リポジトリへの書き込みは Tier C(明示指示が必要)」)
99
99
  - 割り込みで起票する場合の手順は「別パッケージ起因の問題は割り込み Issue で対応する」、分割で起票する場合は下記 epic 節を参照
100
100
 
@@ -104,7 +104,7 @@ Issue には次の要素を必ず含める。
104
104
 
105
105
  なぜ必要か: 分割の根拠を「最初の Issue のコメント」に置くと、その Issue はバッチが最初にマージしてクローズする対象でもあるため、残りの作業の設計図がクローズ済み Issue の中に埋もれる。epic の役割は、その情報の**閉じない置き場**を用意することにある。実行順序は epic が載せられる情報の一つであって、epic が存在する理由ではない。埋没は順序の有無と無関係に、複数分割のたびに起きる。
106
106
 
107
- - **条件分岐を置かない。** 「件数が少ないうちは epic の管理コストが情報整理の利益を上回る」という以前の但し書きは、`scripts/git/git-epic-close.ts`(`pnpm josh followup` から駆動)が子 Issue の全クローズを検知して epic を自動クローズするようになった時点で根拠を失った。放置される epic という管理コストがもう存在しない以上、避けるべきは分岐の誤判定だけである。2 件・順序不問の分割に epic が付く冗長さは軽微で、分岐の見落としによる情報消失より常に安い
107
+ - **条件分岐を置かない。** 「件数が少ないうちは epic の管理コストが情報整理の利益を上回る」という以前の但し書きは、`scripts/epic/epic-close.ts`(`pnpm josh followup` から駆動)が子 Issue の全クローズを検知して epic を自動クローズするようになった時点で根拠を失った。放置される epic という管理コストがもう存在しない以上、避けるべきは分岐の誤判定だけである。2 件・順序不問の分割に epic が付く冗長さは軽微で、分岐の見落としによる情報消失より常に安い
108
108
  - epic には `epic` ラベルを付ける(未作成なら `gh api repos/{owner}/{repo}/labels -f name=epic -f color=5319e7 -f description="Tracks a batch of child issues from one split" --silent 2>/dev/null || true`)。放置された open epic を `gh api "repos/{owner}/{repo}/issues?labels=epic&state=open"` で棚卸しできるようにするため
109
109
  - **epic 自体を実装ランに渡してはならない。** epic には成果物がなく、`backlogrun #<E> --only` がその子 Issue を回す
110
110
  - epic は最後の子 Issue がクローズされた時点で `pnpm josh followup` が自動クローズする。マージ後に `epic` ラベルの open な Issue を探し、タスクリストの子が全てクローズ済みなら子を列挙したコメント付きで閉じる。1 件でも open なら放置し、この処理の失敗は警告のみでランを止めない。最終 PR に `closes #<epic>` を書く方法は、バッチが途中で失敗したときにも発火して未完了を完了扱いにするため採用しない
@@ -131,7 +131,7 @@ pnpm josh epic "<epic-title>" <N1> <N2> --origin <owner/repo#N>
131
131
 
132
132
  このコマンドは上記 4 要件を**構成上**満たす。ラベルを用意してから付与し、子をタスクリスト記法で描画し、`Dependencies` を `--ordered` の有無で矢印連鎖/`None — ...` 固定文に振り分け、`Execution` の実行コマンド(`backlogrun #<E> --only`)を組み立てる。`--ordered` のときは同じ入力から native な依存関係も付与するので、**本文の宣言と native な依存関係が食い違うことがない**(手順 4 の付け忘れが構造的に起きなくなる)。付与は REST の依存関係エンドポイント(`gh api`)を通るため、**`gh` CLI のバージョンには依存しない**(joshuafolkken/kit#1026)。このエンドポイントはブロッカーを Issue 番号ではなく **database id** で受け取り、しかもその id が自リポジトリの Issue かを検証しないため、コマンドは書き込み前に番号から id を解決する。付与は Issue の作成後に独立して行うので、失敗しても件数を報告して続行する(失われるのは関係だけで、Issue とタスクリストは既に正しい)。
133
133
 
134
- 作成済みの epic は `pnpm josh epic:check <E>` で 4 要件を点検できる。手書きした epic、コマンド導入以前の epic、本文を手で編集した後の確認に使う。全要件を満たせば exit 0、満たさなければ exit 1 なのでゲートとしても使える。判定は自動クローズが読むのと**同じパーサ**(`scripts/git/git-epic-parse.ts`)を使うため、「自動クローズが読める形式」と「点検が通る形式」は定義上一致する。
134
+ 作成済みの epic は `pnpm josh epic:check <E>` で 4 要件を点検できる。手書きした epic、コマンド導入以前の epic、本文を手で編集した後の確認に使う。全要件を満たせば exit 0、満たさなければ exit 1 なのでゲートとしても使える。判定は自動クローズが読むのと**同じパーサ**(`scripts/epic/epic-parse.ts`)を使うため、「自動クローズが読める形式」と「点検が通る形式」は定義上一致する。
135
135
 
136
136
  作成手順(フォールバック): **`josh` が使えない環境でのみ**、以下を手で行う。
137
137
 
@@ -13,18 +13,15 @@
13
13
  - 修正できなかった場合: `--notify-message` に失敗チェック名・原因・未解決である旨を記載する。**完了コメントに失敗を隠してはならない**
14
14
  - ユーザーへの報告も失敗の事実を正直に伝える(「成功」として扱わない)
15
15
 
16
- ### auto-merge と `completion` 通知(本文は手順書にある)
16
+ ### ほかの単一ソースにある規則
17
17
 
18
- **auto-merge(`fullrun` の既定)と `completion` 通知の本文は、[`.claude/skills/workflow-commands/followup.md`](../../.claude/skills/workflow-commands/followup.md) にある。** かつてはこのファイルにも「Auto-merge(default for `fullrun`)」「`completion` 通知は `pnpm josh followup` 経由のみ」の 2 節として全文が重複していたが、joshuafolkken/kit#1187 で手順書へ単一ソース化した。`fullrun` と打つこと自体がマージの承認であること、CI がオールグリーンでも未対応の AI レビュー指摘があればマージしないこと、マージ後の `pnpm josh ms`、`completion` Telegram を手で打たないこと、`pnpm josh followup` を前景で実行することは、いずれもそこが単一ソースである。
18
+ このファイルにかつて書き直されていた規則は、次の単一ソースにある。ここには繰り返さない。単一ソース化の経緯は `docs/maintainers/operating-rules-rationale.md` → "Rules that moved to their single source" にある。
19
19
 
20
- ### 明示的な起動が必須(MANDATORY)
21
-
22
- `kickoff` / `halfrun` / `fullrun` / `backlogrun` ワークフロー(`#N` および `new` バリアントを含む)は、ユーザーが**現在のターンのプロンプト**にキーワードを入力していない限り、絶対に開始してはならない。
23
-
24
- - 「実装して」「修正して」「PR を出して」などの会話的な依頼は暗黙の起動ではない。タスクがこれらのワークフローに該当すると判断した場合でも、依頼の形状から起動を推測してはならない
25
- - 「`halfrun new` を実行してもよいですか?」「`fullrun` を回しますか?」のような確認質問もしてはならない。確認プロンプトは明示的な起動の代替にはならない
26
- - 代わりに、**ユーザー自身にコマンドを入力してもらうよう促す**。次の形式を使う: 「このタスクは \`<command>\` で起動してください」。例: 「このタスクは \`halfrun new\` で起動してください」「Issue を実行するには \`fullrun #412\` を実行してください」。ユーザーが次のターンで自分でコマンドを入力する
27
- - 過去のターンで関連ワークフローを承認していた場合でも、このルールは適用される。各起動は現在のターンでユーザーが再入力する必要がある
20
+ - **auto-merge と `completion` 通知** — `.claude/skills/workflow-commands/followup.md` → "`auto-merge` — Default `fullrun` behavior" と `.claude/skills/workflow-commands/followup.md` → "Completion notifications: always via `pnpm josh followup`"
21
+ - **明示的な起動が必須** — `CLAUDE.md` → "Explicit invocation required (MANDATORY)"(常駐)と `.claude/skills/workflow-commands/SKILL.md` → "0. The rule that fires before any of them — explicit invocation"(スキル側の単一ソース)
22
+ - **確認待ちで停止するときの Telegram 通知** — `CLAUDE.md` → "Mid-workflow stop notification (`confirmation`)"
23
+ - **作業ツリーは 1 本のランが保持する(`josh run:hold`)** — `.claude/skills/workflow-commands/working-tree-hold.md` → "The working-tree hold — one run per tree"
24
+ - **overrides の保護** — `.claude/skills/dependency-update/SKILL.md` → "1. Effective overrides live in the workspace — inspect both files"
28
25
 
29
26
  ### 指示されていない行動は取らない
30
27
 
@@ -36,14 +33,13 @@ PR マージ・ブランチ削除・force push・共有ブランチへの push
36
33
  - **`gh pr merge` の直接実行は kit 配布の `.claude/settings.json` の `deny`(`Bash(gh pr merge*)`)で機械的に遮断されている。** `fullrun` の auto-merge は `pnpm josh followup` が node スクリプト内部から gh を起動するため影響を受けない — Bash マッチャに見えるのは `pnpm josh …` だけである。**ただし deny は実装であって規則ではない** — パターンが取りこぼす綴りを禁じているのは本節の規則のほうである
37
34
  - **同じ規則が禁じる force push とブランチ削除も deny に載っている**(joshuafolkken/kit#1062)。`Bash(git push *--force*)` / `Bash(git push * -f)` はフラグを引数の後ろに書いた綴りを、`Bash(git push *--delete*)` / `Bash(git branch -d*)` / `Bash(git branch -D*)` / `Bash(gh api *DELETE*git/refs/heads/*)` はブランチ削除を止める。**deny は規則より狭いが、その差は配送ガードが埋めている** — `git -C` を前置した綴り、短縮フラグをまとめた綴り(`git push -uf`)、`:` をリテラルにできず glob が照合できない `git push origin :branch` は、いずれも `pnpm josh rule:guard` の `git-force` 行が argv を解析して拒否する(joshuafolkken/kit#2120)。**「マージ経路は deny が保証している」とは読まないこと**
38
35
  - **共有状態に影響する操作(このセクションの対象=Tier C)は迷ったら確認する。** 確認のコストは低いが、意図しない操作の巻き戻しは高コスト
39
- - ただしこの「迷ったら確認」は Tier C に限る。**可逆な実装・設計判断(Tier A)は別ルール**(CLAUDE.md「Decision autonomy」の3層ポリシー)に従い、明確に優位な選択肢は確認せず自動で選んで記録する — 本当に甲乙つけがたい(Tier B)ときだけ確認する。下記「意思決定の自律ポリシー」を参照
36
+ - ただしこの「迷ったら確認」は Tier C に限る。**可逆な実装・設計判断(Tier A)は別ルール**(下記「意思決定の自律ポリシー」)に従う
40
37
 
41
38
  ### git index を勝手に変更しない(自律 staging の禁止)
42
39
 
43
- **git の index(ステージング領域)はユーザーのものである。** ユーザーは「後の変更を差分で見るための基準スナップショット」として意図的にステージしていることがあり、`git add` / `git add -A` / `git rm --cached` / `git restore --staged` はそれを上書きする。index には履歴がないため、**上書きされた直前のステージ状態は復元できない**。
40
+ 規則そのもの — index はユーザーのスナップショットであり、自分の判断でステージ・コミットしない — は `CLAUDE.md` → "Git Rules" に常駐している。ここに書くのは、その規則を実行するときの細則である。index には履歴がなく、上書きされた直前のステージ状態は復元できない(経緯は `docs/maintainers/operating-rules-rationale.md` → "Why the index is the user's")。
44
41
 
45
- - **調査目的の staging は絶対に行わない。** 「diff stat を出したい」「未追跡ファイルの中身を差分で見たい」といった理由で `git add` してはならない。これが実際に事故(ユーザーが意図的に作ったスナップショットの破壊)を起こしたケースがある
46
- - **調査は読み取り専用コマンドで行う**:
42
+ - **調査目的の staging は絶対に行わない。** 調査は読み取り専用コマンドで行う:
47
43
  - 変更ファイル一覧: `git status --short`
48
44
  - 作業ツリーの差分: `git diff` / `git diff --stat` / `git diff HEAD`
49
45
  - ステージ済みの差分: `git diff --staged`(読み取りのみ、index は変えない)
@@ -55,69 +51,16 @@ PR マージ・ブランチ削除・force push・共有ブランチへの push
55
51
  - **レーンの中で競合を解決したあとの「解決済み」の記録は、ケース 2 に含まれる(Tier A)。** レーンは run 専用の作業ツリーで、守るべき利用者の staging はない。利用者に `git add` の許可を求めず、`pnpm josh git -y` で記録する。手順は `.claude/skills/workflow-commands/chain-rule.md` →「origin/main is merged in before the gate」の 1 か所にだけ書く(joshuafolkken/kit#2445)
56
52
  - 同じ理由で、`git reset` / `git checkout -- <path>` / `git restore <path>` など index や作業ツリーを破壊的に書き換える操作も、自分の判断で実行しない
57
53
  - **`git stash` は例外的に、明文化されたフローの中でのみ自動実行してよい**: `fullrun new` / `halfrun new` の手順 5(作業ツリーに変更がある状態で `josh latest` を回す前の退避)、`backlogrun` のラン開始時の `josh latest`、「別パッケージ起因の問題は割り込み Issue で対応する」、および `backlogrun` が epic の子を始める前の preflight(`pnpm josh run:hold <N>` が `reclaim` と答えたときの回収 — joshuafolkken/kit#926, joshuafolkken/kit#1965)。**この 5 番目だけが復元を伴わない。前の 4 つはいずれも直後に `pnpm josh stash:pop "<メッセージ>"` で復元することが手順に含まれている**(stash はリポジトリ単位の 1 本のスタックを全 work tree が共有するため、位置指定や引数なしの `git stash pop` は別のレーンが最後に積んだ stash を取り込む — メッセージで対象を特定する。joshuafolkken/kit#2050)。 回収するのは異常終了したランの置き土産であって、いま実行中のランの作業ではないから、pop して戻す先がない。**代わりに stash を子の Issue にコメントで記録する** — 前提 Issue で中断するときの stash(`SKILL.md` §2d)と同じく、**その記録だけが後で pop させられる唯一の手がかり**であり、記録し忘れた stash は誰にも拾われない。これら以外の場面で退避したくなったときは、実行せずに先に確認する
58
- - **この禁止は kit 配布の `.claude/settings.json` の `deny`(`Bash(git add*)` / `Bash(git stage*)` / `Bash(git rm*)` / `Bash(git mv*)` / `Bash(git reset*)` / `Bash(git restore --staged*)` / `Bash(git restore -S*)` / `Bash(git commit*)`)で機械的にも遮断されている。** `pnpm josh git` は node スクリプト内部から git を起動するため影響を受けず、承認済みのコミットフロー(上記ケース 2)は従来どおり動く。**deny には「そのターンでユーザーが明示指示した」という例外がないため、上記ケース 1 も AI 側では実行できない** — その場合はユーザー自身の端末で実行してもらう(ユーザーの手元では従来どおり動く)。恒久的な機械的保証のほうが、コマンド 1 本で回避できる例外より価値が高いという判断(joshuafolkken/kit#850)
59
- - **`Bash(git commit*)` だけはステージング操作ではないが、同じ deny に入っている。** `git add` を拒否されたエージェントが次に手を伸ばすのが `git commit -a`(追跡済みファイルをまとめてステージしてコミットする)であり、それも拒否されると素の `git commit -m` である。フラグ単位で塞いでいる限りこの退避路は最後の 1 本が残るため、joshuafolkken/kit#1075 でサブコマンド全体へ広げた。**ユーザーが明示的にコミットを指示した場合も AI 側では実行できない点は上と同じ** — 承認済みのコミットは `pnpm josh git` を通す
54
+ - **この禁止は kit 配布の `.claude/settings.json` の `deny`(`Bash(git add*)` / `Bash(git stage*)` / `Bash(git rm*)` / `Bash(git mv*)` / `Bash(git reset*)` / `Bash(git restore --staged*)` / `Bash(git restore -S*)` / `Bash(git commit*)`)で機械的にも遮断されている。** `pnpm josh git` は node スクリプト内部から git を起動するため影響を受けず、承認済みのコミットフロー(上記ケース 2)は従来どおり動く。**deny には「そのターンでユーザーが明示指示した」という例外がないため、上記ケース 1 も AI 側では実行できない** — その場合はユーザー自身の端末で実行してもらう。**ユーザーが明示的にコミットを指示した場合も同じで**、承認済みのコミットは `pnpm josh git` を通す(`git commit` まで deny に入れた理由は `docs/maintainers/operating-rules-rationale.md` → "Why the index is the user's")
60
55
  - **「拒否される操作」と「禁止された操作」は同じ集合ではない。** deny に載っているのは上記の直接実行だけだが、このセクションが同じく禁じている `git checkout -- <path>` / `git restore <path>` / 認可外の `git stash`(bare・メッセージ無し push・位置指定 pop など。メッセージ付き `git stash push -m` と `pnpm josh stash:pop` は認可済みなので通る)は、`pnpm josh rule:guard` の `worktree-mutation` 行が拒否する(joshuafolkken/kit#2120)。**ツールが通したことを許可と読み替えてはならない** — 何をしてよいかを決めるのは deny でも配送ガードでもなくこのルールである(フックは Claude Code にしか届かない)
61
- - このルールは横断ドキュメント(CLAUDE.md「Git Rules」→「Never stage or mutate the git index on your own」)のカノニカル参照
62
56
 
63
57
  ### 意思決定の自律ポリシー(確認停止を減らす)
64
58
 
65
- AI ツール(Opus / Gemini / Cursor)が判断の分岐で止まりすぎるのを防ぐため、各判断を3層に分類して扱う。停止して確認するのは**本当にユーザーの判断が必要な分岐だけ**にする。このセクションが横断ドキュメント(CLAUDE.md「Decision autonomy」)のカノニカル参照。
66
-
67
- - **Tier A — 可逆な実装・設計判断**(明確に優位な選択肢があるライブラリ選定、命名、ファイル構成、テスト手法、リファクタの形)。メリット比較で1案が明確に優位なら**確認せず自動で選んで進める**。本来ユーザー確認すべき分岐だった場合は、後から監査・差し戻せるよう判断を記録する(下記「自動判断の記録」)
68
- - **Tier B — 本当に甲乙つけがたい判断**。上位2案がどちらも妥当で差が僅差。**ここだけが停止する層** — ユーザーに確認する(`AskUserQuestion` が使えるなら使う)。拮抗する候補とトレードオフを提示する
69
- - **起票した Issue の所属先は、候補が複数の epic に散っていても Tier B ではない**(joshuafolkken/kit#1339)。`epic --add` 1 回で移せるので推奨する 1 つを選び、採用・却下・理由・決定日を Issue と epic の両方に記録して進む。止まるのは 2 つの epic が本当に甲乙つけがたいときだけである
70
- - **Tier C — 不可逆・共有状態・スコープ外の操作**(マージ、ブランチ削除、force push、破壊的操作、リポジトリ設定変更、タスク範囲外の変更、`devEngines` / overrides の編集(`pnpm-workspace.yaml` `overrides:` と `package.json` `pnpm.overrides` のいずれも))。**このポリシーの対象外。** 1案が明確に優位に見えても、常にユーザーの明示指示を要する。既存の安全ルール(上記「指示されていない行動は取らない」、`devEngines` / overrides 保護)が優先される
71
-
72
- **A と B の判定基準**: 確認するのは「差が僅差 **かつ** 後戻りしにくい/アーキテクチャに長く影響する」ときだけ。「迷っている」だけでは停止理由にならない — 明確に優位な選択肢は多少の不確実性が残っても自動で選び、僅差でも安価に巻き戻せる選択は自動で決めて記録して進む。
73
-
74
- **Tier A に含まれる「自己修正」**: 次の 2 つは設計判断ではなく後始末であり、**確認せずに実行してよい**。
75
-
76
- - **自分が公開した成果物の事実誤りの訂正**: Issue / PR コメントや Issue 本文の誤記・誤った帰属(例: 欠陥を実際とは別のパッケージに帰属させた記述)を、自分で訂正する
77
- - **同じセッションで自分が特定した、自分の作業の抜けの穴埋め**: 例として、欠けていると自分で指摘した相互リンクを後から追加する
78
-
79
- どちらも可逆で、望ましい結果が 1 つしかなく、放置をユーザーが選ぶことはない。**この半分に回避策のリスクはない** — 問題を迂回するのではなく、既に行った作業を修復するだけだからである。
80
-
81
- - **「相談と実行を区別する」との境界**: ここでの Tier A は **すでに承認され実行された作業を完了・修復する**ことに限られる。目標の表明(「〜したい」)や進め方への問い(「どうすべき?」)に対して勝手に動いてよい、という意味ではない(→「相談と実行を区別する(議論中にファイルを編集しない)」)
82
- - **Tier C との境界(再掲)**: 自分のコメントの訂正は Tier A。マージ・ブランチ削除・force push・スコープ外の変更は、**その問題を招いたのが自分自身であっても** Tier C のまま
83
- - 記録は下記「自動判断の記録」に従う。確認を外しても監査証跡は外さない
84
-
85
- **自動判断の記録**: 本来確認すべき Tier A の分岐を自動判断したときは、候補と理由を記録する:
86
-
87
- - Issue 駆動ワークフロー内(`kickoff` / `halfrun` / `fullrun` / `backlogrun`): `pnpm josh issue:comment <N> --body-file <path>` で、採用案・不採用の代替案・なぜ採用案が明確に優位かを記載する
88
- - Issue が存在しない会話タスク: 同じ内容を「Auto-decided: `<choice>` over `<alt>` because `<reason>`」の1行として応答に明示する
89
-
90
- ### 確認待ちで停止するときの Telegram 通知(`confirmation`)
91
-
92
- `kickoff` / `fullrun` 実行中に AI ツールがユーザーの確認・承認・指示待ちで停止するときは、停止の **直前に** Telegram 通知を 1 回送る。これにより、画面を見ていなくてもユーザーが応答すべきタイミングに気付ける。
93
-
94
- ```bash
95
- pnpm josh notify --task-type confirmation --issue-url "<issue-url>" --body=$'<停止理由>\n<ユーザーに求める判断>'
96
- ```
97
-
98
- - 本文が `-` で始まる場合は `--body=...` の形式(1 トークン)で渡す。スペース区切りでは `parseArgs` がエラーになる
99
- - 同一の停止に対して通知は 1 回のみ。再評価のたびに送らない
100
- - ユーザー自身がそのターンで停止を指示した場合は通知しない(既に把握しているため)
101
-
102
- ### 作業ツリーは 1 本のランが保持する(`josh run:hold`)
103
-
104
- 手順の単一ソースは `.claude/skills/workflow-commands/SKILL.md` → 「2f. The working-tree hold — one run per tree」にある。ここに書くのは、キーワードが打たれていないターンでも読まれる位置に、引き金だけを置くためである。
105
-
106
- `fullrun` / `halfrun` は、**他の何よりも先に `pnpm josh run:hold` を実行し、その答えに従う**。`busy` または `unknown` なら、`confirmation` Telegram を送って停止する — **起票もブランチ作成もファイル編集もしない**。`new` 系の入口では起票より前に問う。起票してから気付けば、掃除すべき副作用が残るためである。
107
-
108
- **`kickoff` は対象外である**(joshuafolkken/kit#1799)。このガードが守るのは 1 本のブランチ・1 つの index・1 つの未コミット差分であり、`kickoff` はそのいずれにも触れない — Issue を読み、タイトルを正規化し、計画を投稿し、通知して止まる、そのすべてが GitHub 側の操作である。取得させると、そのランが決して乱さない資源のために、無関係なランの実行中ずっと計画作業が止まっていた。取得しない以上、解除もしない。
109
-
110
- **解除は、どのランのものかを名乗る**(joshuafolkken/kit#1799)。`pnpm josh run:release <N>` は記録が `<N>` を名乗るときだけ削除し、引数なしの形は未採番ランの記録だけを削除する。それ以外のランの記録なら `held` を返して何も消さない。以前はそこにある記録を無条件に消していたため、`busy` の停止メッセージが案内する復旧手順そのものが、稼働中のランの作業ツリーを解放する経路になっていた。本当に放棄された記録を消すのは `pnpm josh run:release --force` だけである。
111
-
112
- **判定の単位は作業ツリーであり、リポジトリではない。** `backlogrun` が使う `epic-busy.ts` はリポジトリに問う読み取りで、「1 リポジトリにつき同時 1 子」を実装している。これらの入口が奪い合う資源は 1 本のブランチ・1 つの index・1 つの未コミット差分であり、別 worktree ならそれらは別々に存在するので競合しない。ここでリポジトリ単位の判定を使うと、正当な 2 本目まで止まる。**`backlogrun` 側の既存ガードは変更しない** — 両者は別の資源を守っており、片方が片方を置き換えることはできない(joshuafolkken/kit#1091)。
113
-
114
- ### overrides の保護(`pnpm-workspace.yaml` / `package.json` の両方を見る)
115
-
116
- overrides に設定された制約は、**セキュリティ・互換性・動作保証のために意図的に追加されたもの**である。
117
-
118
- **実効のある overrides は `pnpm-workspace.yaml` に置く。** pnpm 11 と 12 は `package.json` の旧 `pnpm.overrides` を無視する(pnpm 12.6.0 で実測)。両ファイルの既存宣言を点検して意図しない変更を防ぐが、旧欄を有効な override と数えてはならない。**`pnpm.overrides` が空、あるいは `pnpm` フィールドが無いことは、そのプロジェクトに overrides が無いことの証拠にはならない。** app-kit でも実効のある設定は workspace 側にある(kit #740)。
59
+ 3 層の定義(Tier A / B / C)、起票した Issue の epic 所属と自己修正が Tier A であること、自動判断の記録先は `CLAUDE.md` → "Decision autonomy (minimize confirmation stops)" に常駐している。ここに書くのは、その境界の細則である。
119
60
 
120
- - **確認は「実行するコマンド」であって「到達する結論」ではない。** `josh latest` / `pnpm update --latest` などの依存更新コマンドの実行後は、`git diff -- pnpm-workspace.yaml package.json` を実行し、`overrides:` ブロックと `pnpm.overrides` の双方が無傷であることを確認する
121
- - `josh latest` は overrides の判定を自分で出力する(最後の overrides 行が `✔ overrides unchanged (<n> from <file>)`、変化していれば `⚠ overrides changed` 警告)。`pnpm josh overrides` は実効のある workspace 設定をスナップショットと比較し、無視される package 側の宣言も報告する。**実際に出力された行を引用して報告する**こと — 推測した判定を書いてはならない
122
- - overrides が自動的に変更・削除された場合は、**理由を調査してから**ユーザーに報告し、明示的な承認なしに変更してはならない
123
- - 例: `"esbuild@<=0.24.2": ">=0.25.0"` などのバージョン制約は、Workers ビルド互換性やパッケージの動作保証のために入れてある場合がある
61
+ - **A と B の判定基準**: 確認するのは「差が僅差 **かつ** 後戻りしにくい/アーキテクチャに長く影響する」ときだけ。「迷っている」だけでは停止理由にならない — 明確に優位な選択肢は多少の不確実性が残っても自動で選び、僅差でも安価に巻き戻せる選択は自動で決めて記録して進む
62
+ - **起票した Issue の所属先は、候補が複数の epic に散っていても Tier B ではない**(joshuafolkken/kit#1339)。`epic --add` 1 回で移せるので推奨する 1 つを選び、採用・却下・理由・決定日を Issue と epic の両方に記録して進む。止まるのは 2 つの epic が本当に甲乙つけがたいときだけである
63
+ - **自己修正**は設計判断ではなく後始末である — 自分が公開した成果物の事実誤り(誤った帰属を含む)の訂正と、同じセッションで自分が特定した自分の作業の抜けの穴埋め(例: 欠けていると自分で指摘した相互リンクの追加)。どちらも可逆で、望ましい結果が 1 つしかなく、問題を迂回せず既に行った作業を修復するだけなので、回避策のリスクはない
64
+ - **「相談と実行を区別する」との境界**: ここでの Tier A は **すでに承認され実行された作業を完了・修復する**ことに限られる。目標の表明(「〜したい」)や進め方への問い(「どうすべき?」)に対して勝手に動いてよい、という意味ではない(→ `principles.md` → "相談と実行を区別する")
65
+ - **Tier C との境界**: 自分のコメントの訂正は Tier A。マージ・ブランチ削除・force push・スコープ外の変更は、**その問題を招いたのが自分自身であっても** Tier C のまま。確認を外しても監査証跡は外さない
66
+ - **自動判断の記録の書き方**: Issue 駆動ワークフロー内では `pnpm josh issue:comment <N> --body-file <path>` で、採用案・不採用の代替案・なぜ採用案が明確に優位かを記載する
@@ -0,0 +1,74 @@
1
+ # 原則
2
+
3
+ **このファイルは、`CLAUDE.md` の Communication 節が指す 7 つの原則の単一ソースである。** 各節は `CLAUDE.md` から `prompts/collaboration-workflow/principles.md` → "見出し" の形で引かれ、`pnpm josh doc:section` で解決する。経緯と適用例は各節が指す [`docs/maintainers/principles-rationale.md`](../../docs/maintainers/principles-rationale.md) の節にあり、実行中には読まない。
4
+
5
+ ## クローン禁止・単一ソース化(パッケージ境界を越えても)
6
+
7
+ 既存の非自明なロジックを「ソースを変えずに済ませる」ために**コピー・移植・再実装することは既定で禁止**する。すでにどこか(別ファイル・別モジュール・別**パッケージ=上流依存を含む**)に存在するロジックを複製しようとした瞬間が、**単一ソース化**(全消費者が import する共有モジュール/export/パッケージ)のシグナルである。コピーではなく単一ソース化する。
8
+
9
+ - **既存の重複は再重複の免罪符にならない**: すでに一度クローンされている(例: jgame が kit をコピー)なら、共有抽象化はとっくに必要だったということ。3 つ目のコピーを足さず、重複の存在を surface する
10
+ - **「上流を参照する」は「再利用する」の意**であって、「そのコードを貼り付ける」ではない
11
+ - **「X を触るな」という制約はクローンを黙って正当化しない**: クリーンな修正には上流(kit)の変更が要る/代替はクローン、というトレードオフを先にユーザーへ提示する(「クリーンな修正は kit の変更が必要、代替はクローン、どちらにする?」)
12
+ - 複製は、単一ソース化の代替案とそのコストを提示し、**ユーザーの明示承認を得た後にのみ**行う
13
+
14
+ **計測は `pnpm josh clone:scan`。** 同一リポジトリ内および `JOSH_REPO_PATHS` の他リポジトリを跨いだ複製を検出し、**件数**と各複製の `file:line`(`[same-file|cross-file|cross-repo]` 分類つき、複製なしは `clean`)を印字する。`pnpm josh oracle:list` に載る決定オラクルでもある(導入の経緯は `docs/maintainers/principles-rationale.md` → "Why clone:scan exists")。
15
+
16
+ ## 設計はエレガント・シンプルを第一目標にする
17
+
18
+ 新しい仕組み(フック・ガード・ルール・抽象化)を足す前に、**原因側を直せばその仕組みが要らなくならないか**を先に問う。要らなくなるなら、足さない。症状を叱る仕組みを重ねるのではなく、症状を生んでいる材料を断つ。
19
+
20
+ - **問いは 1 つ**: 「この仕組みは、どこかの原因を直せば不要にならないか」。答えが「不要になる」なら、仕組みではなく原因を直す。
21
+ - **足す前に断つ**: 検出・通知・叱責を強化する前に、その入力を生んでいる側を探す。入力が消えれば、それを捌く仕組みそのものが消える。適用例は `docs/maintainers/principles-rationale.md` → "An application of simplicity-first"。
22
+
23
+ **書かれたコードの可読性**(意図が伝わる命名、過度な抽象化を避ける、など)は `prompts/coding-standards.md` の担当で、こちらは**設計時にどの仕組みを足すか・どこへ置くかを決める**規則。両者は別レイヤーなので、片方の本文をもう片方へ写さず、互いを指すだけにする。
24
+
25
+ ## 相談と実行を区別する(議論中にファイルを編集しない)
26
+
27
+ ユーザーが「どう進めるべきか」「何をすべきか」「なぜそうなったか」を尋ねたり、目標・願望を述べたりした(「どうすべき?」「how should we…」「なぜ」「理由を知りたい」「〜したい」「〜の方が良い?」)ときは、**分析と推奨のみ**で応答する。ファイル編集・Issue 作成・その他の具体的アクションは取らない。
28
+
29
+ - 具体的アクションを取ってよいのは、明示的な命令(「do it」「書き換えて」「作成して」「implement」)またはワークフローキーワード(`kickoff` / `halfrun` / `fullrun` / `backlogrun`)があるときだけ
30
+ - 曖昧なときは propose-and-wait を既定とする(「これを実行してよいか?」と尋ねる)
31
+ - **目標の表明は「計画の依頼」であって「実行の承認」ではない**
32
+
33
+ ## 最新優先・fix-forward(pin-back は最終手段)
34
+
35
+ 依存パッケージ・ツールチェーンは**既定で最新版を採用する**。バンプが lint クラッシュ・新規有効化ルール・型エラーなどの破壊を引き起こしても、古いバージョンへ留まる/戻すことを既定の「安全策」にしてはならない。破壊は**前向きに(fix-forward)速やかに**解消する。
36
+
37
+ 1. **最新優先(latest-first)**: 依存・ツールチェーンは新しいバージョンを既定で採用する。適応の手間を避けるためだけに古いバージョンに留まったり戻したりしない
38
+ 2. **破壊は fix-forward**: バンプで lint クラッシュ・新規ルール・型エラー等が出たら、前向きに解消する:
39
+ - 新ルール/エラーが正当なら **消費者コードを直す**
40
+ - ルール上書きが要るなら **正しいレイヤー**(kit / app-kit の共有設定)でスコープする。消費者リポジトリでの場当たり的な一回限りの disable にしない
41
+ - 破壊が first-party パッケージ(kit / app-kit)起因なら、**そこに Issue を立てて適切な altitude で直す**。消費者側の回避だけで済ませない(→ `upstream-interrupt.md`)
42
+ 3. **pin-back は最終手段**: fix-forward が本当に不可能/ブロックされている(例: 未リリースの上流修正待ち)ときだけ、古いバージョンへ固定する。固定するときは **理由を記録し、最新へ戻すためのトラッキング Issue を立てる**。pin-back を既定の推奨として提示してはならない
43
+ 4. **既存の保護を尊重する**: fix-forward は保護された pin を黙って書き換える許可ではない。overrides と `devEngines` の承認ゲートの単一ソースは `CLAUDE.md` → "Dependency overrides" と `dependency-update` skill である
44
+ 5. **タイムリーに**: バンプ起因の破壊は、可能な限り同じ作業セッション内で速やかに対処し、pin の裏に先送りしない
45
+
46
+ ## 恒久ルールは MEMORY ではなくプロンプト/ドキュメントに書く
47
+
48
+ 今後のセッションでも守るべき恒久的な振る舞いのルールに気付いたときは、**kit が配布するプロンプト/ドキュメント**(`CLAUDE.md` / `prompts/*`)への変更として記述する。プロジェクト単位の自動 MEMORY(例: `~/.claude/projects/<repo-slug>/memory/`)への保存で済ませてはならない。
49
+
50
+ - **プロンプト/ドキュメントが正である理由**: バージョン管理下でレビューでき、`josh sync` で全消費者リポジトリ・別の PC・別の AI ツールに届き、`git log` で経緯を追える
51
+ - **MEMORY は 1 台のマシン × 1 つのリポジトリ**にスコープされたローカルストアで、コミットされない。保存は最小限に留め、用途は本質的にローカルな文脈(マシン固有のパス、個人の環境の癖など)だけ。どこでも適用されるべきルールの唯一の置き場所にしてはならない
52
+
53
+ 運用:
54
+
55
+ 1. 恒久ルールに気付いたら、まず「これは kit のドキュメント/プロンプトに書くべきか?」を判定する。共有価値があるなら答えは常に yes
56
+ 2. 現在のターンがドキュメント変更を承認していない(相談中など)場合は、**MEMORY に黙って保存せず、プロンプト/ドキュメント変更を提案する**(→「相談と実行を区別する」「配布ドキュメント・設定の変更は kit に上流化する」)
57
+ 3. 消費者リポジトリで気付いた場合は、ローカル編集ではなく kit 側へ Issue/PR として上流化する
58
+ 4. 既に MEMORY にあるルールが実は共有すべきものだと分かったときは、プロンプト/ドキュメントへ移し、MEMORY 側の重複エントリは削除する
59
+
60
+ ## 配布ドキュメント・設定の変更は kit に上流化する
61
+
62
+ `CLAUDE.md` および kit が配布する他のドキュメント/設定は、kit から単一ソースで配布される。
63
+
64
+ - **消費者リポジトリ(app-kit / game-kit)ではこれらをローカル編集しない**: `josh sync` が編集を上書きするうえ、変更は本来上流(kit)に属する。ドキュメント/設定を編集する前に、それが配布物かどうかを確認し、配布物なら kit 側に変更を提案(Issue/PR)する
65
+ - **kit リポジトリ自身ではあなたが配布元**なので、ここでは編集してよい。編集先は `CLAUDE.md` 1 本である(次節)
66
+
67
+ ## エージェント規則の単一ソースは `CLAUDE.md`(`AGENTS.md` / `GEMINI.md` は導線)
68
+
69
+ **規則の本体は `CLAUDE.md` にしか無い。** `AGENTS.md` と `GEMINI.md` は「規則は `CLAUDE.md` にある。作業前に全文を読むこと」と「規則を書き戻さない」だけを書いた短い導線文書であり、規則を 1 行も持たない。
70
+
71
+ - **規則の追加・仕様変更・文言修正・節の追加は `CLAUDE.md` に 1 回だけ書く。** 他の 2 本には触れない
72
+ - **導線文書に規則を書き戻さない。** そこに書かれた規則は、次の改訂で更新し忘れる 4 つ目の置き場になる
73
+ - `scripts/document/ai-document-pointers.test.ts` が機械的に守る。導線文書に規則本体が再出現した場合、導線の一文が消えた場合、`CLAUDE.md` が単一ソースであることの記述が消えた場合に落ちる
74
+ - 経緯は `docs/maintainers/principles-rationale.md` → "Why AGENTS and GEMINI are pointers"、`@CLAUDE.md` 行と他ツールでの未検証は `docs/maintainers/principles-rationale.md` → "The include line, and what has not been verified"