@joshuafolkken/kit 1.1455.0 → 1.1471.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 (211) hide show
  1. package/.claude/skills/dependency-update/SKILL.md +26 -55
  2. package/.claude/skills/epic-commands/SKILL.md +87 -148
  3. package/.claude/skills/epic-commands/epic-bundle.md +45 -77
  4. package/.claude/skills/epic-commands/execution-waves.md +44 -81
  5. package/.claude/skills/verify-ui/SKILL.md +25 -50
  6. package/.claude/skills/workflow-commands/background-commands.md +36 -47
  7. package/.claude/skills/workflow-commands/backlogrun-child.md +72 -85
  8. package/.claude/skills/workflow-commands/backlogrun-lanes.md +91 -121
  9. package/.claude/skills/workflow-commands/backlogrun-park.md +73 -117
  10. package/.claude/skills/workflow-commands/backlogrun-progress.md +7 -9
  11. package/.claude/skills/workflow-commands/backlogrun-recovery.md +11 -20
  12. package/.claude/skills/workflow-commands/backlogrun-steps.md +43 -52
  13. package/.claude/skills/workflow-commands/chain-rule.md +24 -34
  14. package/.claude/skills/workflow-commands/followup.md +57 -76
  15. package/.claude/skills/workflow-commands/issue-comments.md +43 -60
  16. package/.claude/skills/workflow-commands/kickoff.md +65 -74
  17. package/.claude/skills/workflow-commands/observation-filing.md +62 -107
  18. package/.claude/skills/workflow-commands/observation-ledger.md +56 -111
  19. package/.claude/skills/workflow-commands/pre-gate-cut.md +89 -138
  20. package/.claude/skills/workflow-commands/prerequisite.md +10 -15
  21. package/.claude/skills/workflow-commands/progress-watcher.md +21 -26
  22. package/.claude/skills/workflow-commands/retrospective.md +31 -50
  23. package/.claude/skills/workflow-commands/split-assessment.md +34 -58
  24. package/.claude/skills/workflow-commands/working-tree-hold.md +54 -71
  25. package/CLAUDE.md +6 -5
  26. package/dist/CLAUDE.md +6 -5
  27. package/dist/hooks/batch-guard.js +6 -6
  28. package/dist/hooks/{chunk-7WQBPLUN.js → chunk-43ZHT22P.js} +31 -15
  29. package/dist/hooks/{chunk-LIAFCXL7.js → chunk-AS74OU3D.js} +23 -7
  30. package/dist/hooks/{chunk-3C4XRYG6.js → chunk-E7OIKX5Z.js} +17 -12
  31. package/dist/hooks/{chunk-Z4XI7CZS.js → chunk-EUMACUK2.js} +18 -12
  32. package/dist/hooks/{chunk-WNLVGT7E.js → chunk-H5HVWYXK.js} +4 -4
  33. package/dist/hooks/{chunk-HHI6FO3R.js → chunk-IIGFYXKC.js} +345 -240
  34. package/dist/hooks/{chunk-GPLGZ6IC.js → chunk-J47HU5H5.js} +14 -3
  35. package/dist/hooks/{chunk-OLMO72ON.js → chunk-K4EOONYM.js} +1 -1
  36. package/dist/hooks/{chunk-D5QBTOCZ.js → chunk-K4LMBQC2.js} +4 -4
  37. package/dist/hooks/{chunk-TBJFTSUY.js → chunk-KC5AK2GF.js} +8 -6
  38. package/dist/hooks/chunk-SHGPANFB.js +56 -0
  39. package/dist/hooks/{chunk-5H4SSDSD.js → chunk-YHBZAJSV.js} +3 -3
  40. package/dist/hooks/{chunk-HFGWYGUV.js → chunk-YYPI7SJZ.js} +5 -5
  41. package/dist/hooks/codex-hook-adapter.js +13 -13
  42. package/dist/hooks/duplicate-read-guard.js +7 -7
  43. package/dist/hooks/format-edited.js +3 -3
  44. package/dist/hooks/inputs.json +216 -214
  45. package/dist/hooks/investigation-guard.js +7 -7
  46. package/dist/hooks/pretool-guard.js +12 -12
  47. package/dist/hooks/session-lang.js +6 -5
  48. package/dist/hooks/stop-guard.js +18 -14
  49. package/dist/josh.js +5 -6
  50. package/dist/managed-marker/index.js +1 -2
  51. package/dist/version/index.js +15 -12
  52. package/eslint/base.js +2 -1
  53. package/eslint/rules/unicorn.js +16 -0
  54. package/package.json +3 -3
  55. package/prompts/coding-standards.md +12 -22
  56. package/prompts/collaboration-workflow/file-edits.md +26 -44
  57. package/prompts/collaboration-workflow/gh-rest.md +20 -36
  58. package/prompts/collaboration-workflow/glossary.md +5 -7
  59. package/prompts/collaboration-workflow/issue-citation.md +7 -13
  60. package/prompts/collaboration-workflow/issue-template.md +29 -29
  61. package/prompts/collaboration-workflow/operating-rules.md +35 -44
  62. package/prompts/collaboration-workflow/output-bounds.md +15 -15
  63. package/prompts/collaboration-workflow/overview.md +14 -19
  64. package/prompts/collaboration-workflow/plan-comment.md +13 -13
  65. package/prompts/collaboration-workflow/principles.md +50 -53
  66. package/prompts/collaboration-workflow/proposal-request.md +1 -9
  67. package/prompts/collaboration-workflow/report-format.md +32 -49
  68. package/prompts/collaboration-workflow/residency.md +10 -10
  69. package/prompts/collaboration-workflow/rule-delivery.md +9 -9
  70. package/prompts/collaboration-workflow/shell-body.md +10 -20
  71. package/prompts/collaboration-workflow/turn-batching.md +8 -14
  72. package/prompts/collaboration-workflow/upstream-interrupt.md +26 -34
  73. package/prompts/collaboration-workflow/wip-cap.md +24 -30
  74. package/prompts/collaboration-workflow.md +24 -25
  75. package/prompts/refactoring.md +33 -43
  76. package/prompts/review-rubric.md +84 -129
  77. package/prompts/review.md +111 -141
  78. package/prompts/sonar-hotspot-handling.md +22 -50
  79. package/prompts/testing-guide.md +48 -99
  80. package/scripts/adopt/adopt-toolkits.ts +2 -4
  81. package/scripts/agent/agent-exit-record.ts +23 -1
  82. package/scripts/agent/codex-agent-argv.ts +7 -2
  83. package/scripts/backlog/backlog-budget-cli.ts +1 -2
  84. package/scripts/backlog/backlog-drive-carried.ts +26 -0
  85. package/scripts/backlog/backlog-drive-cli.ts +10 -5
  86. package/scripts/backlog/backlog-drive-named.ts +2 -4
  87. package/scripts/backlog/backlog-drive-restore.ts +19 -1
  88. package/scripts/backlog/backlog-drive-seats.ts +27 -0
  89. package/scripts/backlog/backlog-drive.ts +11 -6
  90. package/scripts/backlog/backlog-ready.ts +13 -6
  91. package/scripts/behavior/behavior-rules.ts +3 -2
  92. package/scripts/cost-runtime/codex-usage.ts +4 -2
  93. package/scripts/cost-runtime/cost-cli.ts +1 -2
  94. package/scripts/delegation/investigation-guard.ts +1 -1
  95. package/scripts/delegation/investigation-reads.ts +1 -1
  96. package/scripts/discovery/repo-discovery.ts +4 -2
  97. package/scripts/discovery/repo-origin.ts +2 -4
  98. package/scripts/doctor/doctor-logic.ts +6 -3
  99. package/scripts/document/document-byte-budget.ts +27 -27
  100. package/scripts/document/document-byte-check.ts +1 -2
  101. package/scripts/document/entry-read-budget.ts +2 -2
  102. package/scripts/epic/epic-audit-rationale.ts +8 -2
  103. package/scripts/epic/epic-bundle-cli.ts +1 -2
  104. package/scripts/epic/epic-chains.ts +6 -2
  105. package/scripts/epic/epic-close-comment.ts +1 -2
  106. package/scripts/gate/verification-gate.ts +7 -2
  107. package/scripts/gh/git-pr.ts +6 -2
  108. package/scripts/git/git-common-directory.ts +3 -3
  109. package/scripts/git/git-diff-reads.ts +16 -9
  110. package/scripts/git/git-execa-error.ts +1 -2
  111. package/scripts/hooks/format-edited-file.ts +10 -4
  112. package/scripts/hooks/pre-push-unit.ts +15 -4
  113. package/scripts/hooks/pretool-guard.ts +23 -29
  114. package/scripts/hooks/step-zero-notice.ts +3 -2
  115. package/scripts/init/hook-command-rewrite.ts +6 -2
  116. package/scripts/init/init-logic-deploy-vps.ts +4 -2
  117. package/scripts/issue/behavior-change-lint.ts +12 -6
  118. package/scripts/issue/issue-scout-cli.ts +3 -2
  119. package/scripts/josh/file-map-stamp.ts +1 -3
  120. package/scripts/josh/hook-decision.ts +17 -2
  121. package/scripts/lane/lane-await.ts +3 -2
  122. package/scripts/lane/lane-child-invocation.ts +14 -1
  123. package/scripts/lane/lane-guard-policy.ts +4 -4
  124. package/scripts/lane/lane-ledger.ts +9 -0
  125. package/scripts/lane/lane-load.ts +9 -2
  126. package/scripts/lane/lane-measure-cli.ts +2 -0
  127. package/scripts/lane/lane-parked.ts +18 -0
  128. package/scripts/lane/lane-process-load.ts +125 -0
  129. package/scripts/lane/lane-process-stats.ts +93 -0
  130. package/scripts/lane/lane-registry.ts +8 -3
  131. package/scripts/lane/lane-session-broker.ts +29 -5
  132. package/scripts/lane/lane-spent.ts +14 -3
  133. package/scripts/lane/lane-stats.ts +1 -0
  134. package/scripts/managed-marker/managed-marker-logic.ts +1 -2
  135. package/scripts/overrides/lockfile-overrides.ts +1 -3
  136. package/scripts/propagate/propagate.ts +1 -2
  137. package/scripts/release/release-progress.ts +3 -2
  138. package/scripts/report/report-lint.ts +7 -4
  139. package/scripts/review/review-record-cli.ts +6 -2
  140. package/scripts/rules/destructive-command.ts +6 -9
  141. package/scripts/rules/direct-filing.ts +3 -7
  142. package/scripts/rules/early-heartbeat.ts +7 -18
  143. package/scripts/rules/file-body.ts +6 -13
  144. package/scripts/rules/filing-cap.ts +3 -6
  145. package/scripts/rules/git-force.ts +5 -9
  146. package/scripts/rules/implementation-cut.ts +37 -35
  147. package/scripts/rules/index-guard.ts +4 -7
  148. package/scripts/rules/issue-comments.ts +5 -15
  149. package/scripts/rules/josh-git-bare.ts +3 -6
  150. package/scripts/rules/lane-background.ts +10 -21
  151. package/scripts/rules/lane-carry-conflict.ts +7 -17
  152. package/scripts/rules/lane-interactive-ask.ts +6 -11
  153. package/scripts/rules/lane-park.ts +5 -13
  154. package/scripts/rules/lane-split-park.ts +2 -7
  155. package/scripts/rules/lane-switch-main.ts +9 -12
  156. package/scripts/rules/oracle-consulted.ts +4 -5
  157. package/scripts/rules/piped-verification.ts +81 -31
  158. package/scripts/rules/poll-loop.ts +7 -17
  159. package/scripts/rules/pre-gate-cut.ts +7 -21
  160. package/scripts/rules/prior-comment-read.ts +7 -5
  161. package/scripts/rules/protected-files.ts +5 -9
  162. package/scripts/rules/raw-field-body.ts +3 -7
  163. package/scripts/rules/rule-body-guard.ts +4 -11
  164. package/scripts/rules/run-tail-rule.ts +6 -22
  165. package/scripts/rules/shell-body-trigger.ts +4 -6
  166. package/scripts/rules/shell-segments.ts +7 -0
  167. package/scripts/rules/stop-rules.ts +16 -29
  168. package/scripts/rules/test-declared-commit.ts +4 -10
  169. package/scripts/rules/third-party-write.ts +5 -10
  170. package/scripts/rules/worktree-guard.ts +5 -12
  171. package/scripts/run/board/run-board-github.ts +11 -3
  172. package/scripts/run/board/run-board-idle.ts +31 -0
  173. package/scripts/run/board/run-board-read.ts +9 -12
  174. package/scripts/run/board/run-board-reason.ts +7 -3
  175. package/scripts/run/board/run-board-state.ts +4 -0
  176. package/scripts/run/board/run-board-status.ts +18 -3
  177. package/scripts/run/board/run-board-thanks.ts +7 -2
  178. package/scripts/run/board/run-board-tick.ts +32 -7
  179. package/scripts/run/carry/run-carry-args.ts +1 -3
  180. package/scripts/run/carry/run-carry-conversation.ts +7 -2
  181. package/scripts/run/cut/run-cut-cli.ts +15 -20
  182. package/scripts/run/cut/run-cut-decline.ts +72 -0
  183. package/scripts/run/cut/run-cut-ready.ts +74 -0
  184. package/scripts/run/cut/run-cut-report.ts +13 -0
  185. package/scripts/run/cut/run-cut.ts +10 -1
  186. package/scripts/run/hold/run-hold-cli.ts +14 -3
  187. package/scripts/run/hold/run-hold.ts +6 -3
  188. package/scripts/run/merge/run-merge-cli.ts +30 -7
  189. package/scripts/run/merge/run-merge-ship.ts +59 -1
  190. package/scripts/run/merge/run-merge.ts +3 -2
  191. package/scripts/run/run-ending.ts +31 -3
  192. package/scripts/run/run-parent-cut-hook.ts +5 -10
  193. package/scripts/run/run-preflight.ts +1 -2
  194. package/scripts/run/run-stop-notify.ts +1 -2
  195. package/scripts/run/run-watcher-guard.ts +6 -3
  196. package/scripts/run/ship/run-ship-review-steps.ts +13 -4
  197. package/scripts/run/ship/run-ship-review.ts +15 -2
  198. package/scripts/run/tidy/run-tidy-cli.ts +3 -3
  199. package/scripts/run/tidy/run-tidy-lanes.ts +3 -2
  200. package/scripts/safe-chain/project-config.ts +7 -2
  201. package/scripts/sync/sync-hook-safety.ts +8 -2
  202. package/scripts/test/unit-worker-share.ts +3 -2
  203. package/scripts/time-runtime/time-batch-guard.ts +3 -3
  204. package/scripts/time-runtime/time-hook-transcript.ts +3 -2
  205. package/scripts/time-runtime/time-shell.ts +10 -0
  206. package/scripts/version/effective-upstream.ts +3 -4
  207. package/scripts/version/kit-version-config.ts +8 -2
  208. package/scripts/version/latest-corepack.ts +1 -2
  209. package/scripts/version/release-hold.ts +11 -4
  210. package/scripts/version/version-commands.ts +12 -4
  211. package/dist/hooks/chunk-UT7YC3N2.js +0 -56
@@ -1,99 +1,82 @@
1
1
  # An Issue's comments are part of the Issue
2
2
 
3
- **The single source of the comment read**, read at its point of use — before implementing a `#N`
4
- Issue. Rationale and history: `docs/maintainers/issue-comments-rationale.md` → "Why comments are read".
3
+ **The single source of the comment read**, read before implementing a `#N` Issue. Rationale and
4
+ history: `docs/maintainers/issue-comments-rationale.md` → "Why comments are read".
5
5
 
6
6
  **Every `#N` entry point reads the Issue's comments before it implements** — `fullrun`, `halfrun` and
7
- `kickoff`; a `backlogrun` named issue and epic child inherit it through `fullrun`'s procedure. The read
8
- is one call, made in the same turn as whatever else the run already needs:
7
+ `kickoff`; a `backlogrun` named issue and epic child inherit it through `fullrun`. One call, in the same
8
+ turn as whatever else the run needs:
9
9
 
10
10
  ```bash
11
11
  pnpm josh issue:read <N> [<N> ...] # body and comments, one call per batch
12
12
  gh api repos/{owner}/{repo}/issues/<N>/comments --jq '.[] | {user: .user.login, created_at, body}'
13
13
  ```
14
14
 
15
- **The first line is the one to type**; `pnpm josh issue:read` answers the body and the comments for
16
- every number named, in one call, and **says when a comment listing could not be read rather than
17
- showing no comments**. The `gh api` form stays for a **cross-repository** read: the command takes no
18
- `--repo`. Never `gh issue view <N> --comments` — it is GraphQL-backed and a cloud session is answered
19
- `403`.
15
+ **Type the first line**; it **says when a comment listing could not be read rather than showing no
16
+ comments**. The `gh api` form is for a **cross-repository** read (the command takes no `--repo`). Never
17
+ `gh issue view <N> --comments` — GraphQL-backed, `403` in a cloud session.
20
18
 
21
19
  **This repository writes its agreements into comments and then reads only bodies.** **What the
22
- reading is for**, so it is not skimmed: the boundary of the scope — work a comment moved to
23
- another Issue, or added to this one; the record of an auto-decision already made; a split or epic
24
- agreement reached after filing; a recorded stash or an in-flight branch; and a **correction of the
20
+ reading is for**: the scope boundary — work a comment moved elsewhere or added here; an auto-decision
21
+ already made; a split or epic agreement; a recorded stash or in-flight branch; a **correction of the
25
22
  body's own diagnosis**.
26
23
 
27
24
  ## When a comment contradicts the body
28
25
 
29
- **The later text is the agreement in force.** A body is written first and is not rewritten when a
30
- decision arrives, so of a body and a comment that disagree the comment is the newer of the two and
31
- wins. **This is settled by ordering, never by judging which reads better.** Name in the two-layer work
32
- summary which comment superseded what.
26
+ **The later text is the agreement in force** — the comment is the newer, so it wins. **This is settled
27
+ by ordering, never by judging which reads better.** Name in the work summary which comment superseded
28
+ what.
33
29
 
34
30
  **Two answers are not the run's to make, and each is decided from what the comment says:**
35
31
 
36
- - **A comment that reassigns part of the scope to another Issue** takes that part out of scope: do not
37
- implement it, whatever acceptance criteria the body still lists, and name the Issue it went to in the
38
- completion report.
32
+ - **A comment that reassigns part of the scope to another Issue** takes that part out of scope, whatever
33
+ the body's criteria say; name the Issue it went to in the completion report.
39
34
  - **A comment saying the Issue no longer has a reason to exist** — the defect does not reproduce, or it
40
- was fixed elsewhere — takes the exit in the next subsection, "When the work turns out to be already
41
- merged". Closing an Issue is Tier C.
35
+ was fixed elsewhere — takes the exit in "When the work turns out to be already merged". Closing an
36
+ Issue is Tier C.
42
37
 
43
- Everything else is the ordinary work of the run, **a widened scope included**: a widening large enough
44
- to be several separately-mergeable deliverables is the split assessment's business
45
- (`split-assessment.md`), not a second kind of stop.
38
+ Everything else, **a widened scope included**, is ordinary work; a widening into several
39
+ separately-mergeable deliverables is the split assessment's business (`split-assessment.md`).
46
40
 
47
41
  ## When the work turns out to be already merged
48
42
 
49
- **A run can learn its Issue is already done in two ways, and both end here.** A **comment** says so —
50
- the bullet above — or the **run itself verifies it**, by reading the merged code and finding every
51
- acceptance criterion already satisfied. What is left to do afterwards is identical, so there is one
52
- procedure and not two. **Parking it is not the place**: `needs-decision` means "waiting for an answer
53
- nobody has given", and here the answer exists.
43
+ **A comment says so, or the run itself verifies it** by finding every acceptance criterion already
44
+ satisfied in merged code — one procedure either way. **Parking it is not the place**: `needs-decision`
45
+ means "waiting for an answer", and here the answer exists.
54
46
 
55
- **The exit is the `already-done` label.** It is `needs-decision`'s counterpart: `epic:next`,
56
- `backlog:next` and `auto-ok:next` all stop offering the Issue (`scripts/issue/issue-labels.ts` →
57
- `NOT_DIRECTLY_RUNNABLE_LABELS`, `epic-classify.ts` → `human`), and `epic:busy` stops counting it as
58
- holding a lane. **Only a person removes it, by closing the Issue.**
47
+ **The exit is the `already-done` label.** `epic:next`, `backlog:next` and `auto-ok:next` stop offering
48
+ the Issue (`scripts/issue/issue-labels.ts` → `NOT_DIRECTLY_RUNNABLE_LABELS`, `epic-classify.ts` →
49
+ `human`), and `epic:busy` stops counting it. **Only a person removes it, by closing the Issue.**
59
50
 
60
51
  ```bash
61
52
  gh api repos/{owner}/{repo}/labels -f name=already-done -f color=6f42c1 -f description="Verified already merged — a person closes it" --silent 2>/dev/null || true
62
53
  gh api repos/{owner}/{repo}/issues/<N>/labels -f 'labels[]=already-done'
63
54
  ```
64
55
 
65
- The procedure, in order:
66
-
67
- 1. **Record the evidence as an Issue comment, before the label.** Name the pull request or commit that
68
- merged the work and, for each acceptance criterion the Issue states, the file and lines that satisfy
69
- it. **A claim with no citations is not the finding this exit is for.**
56
+ 1. **Record the evidence as an Issue comment, before the label**: the merging pull request or commit
57
+ and, per acceptance criterion, the file and lines that satisfy it. **A claim with no citations is not
58
+ the finding this exit is for.**
70
59
  2. **Apply `already-done`** — the two commands above.
71
- 3. **Commit nothing, push nothing, open no pull request.** The tree is clean, so release the hold with
72
- `pnpm josh run:release <N>`, which also removes `in-progress` — left on, it holds a lane against an
73
- Issue nothing will ever run.
74
- 4. **Then behave as the entry point does for a parked child.** A `fullrun` / `halfrun` a person typed
75
- sends a `confirmation` Telegram naming the Issue and the merge that already covers it, and stops. An
76
- `backlogrun` child is park-and-continue (`backlogrun-park.md` → "park and continue").
77
- 5. **Never close the Issue.** That is Tier C at every entry point, and the label leaves the close one
78
- click away for the person who owns it.
79
-
80
- **Nothing about this is a license to skip the work when it merely looks familiar.** The bar is step 1's
81
- citations: a criterion you cannot point at merged code for is a criterion this run still owes.
60
+ 3. **Commit nothing, push nothing, open no pull request.** Release the hold with
61
+ `pnpm josh run:release <N>`, which also removes `in-progress`.
62
+ 4. **Then behave as the entry point does for a parked child.** A typed `fullrun` / `halfrun` sends a
63
+ `confirmation` Telegram naming the Issue and the covering merge, and stops; a `backlogrun` child is
64
+ park-and-continue (`backlogrun-park.md` → "park and continue").
65
+ 5. **Never close the Issue** — Tier C at every entry point.
66
+
67
+ **Looking familiar is no license to skip the work**: a criterion you cannot point at merged code for is
68
+ one this run still owes.
82
69
 
83
70
  ## A long thread
84
71
 
85
- **The fetch is one call however long the thread is; what costs is carrying it afterwards** — which is
86
- why the call above projects each comment down to its author, its timestamp and its body. Once the
87
- thread runs longer than the Issue itself it is exactly the pre-implementation reading `delegation.md` describes:
88
- brief a delegated unit to return **the agreements in force plus the comment URLs that carry them**,
89
- never the comment text.
72
+ **The fetch is one call; what costs is carrying it** — hence the projection to author, timestamp and
73
+ body. A thread longer than the Issue is the pre-implementation reading `delegation.md` describes: brief
74
+ a unit to return **the agreements in force plus the comment URLs that carry them**, never the text.
90
75
 
91
- **`pnpm josh rule:guard` refuses the body-only read** and hands over the reissue and the conflict rule
92
- at the moment they bind (`prompts/collaboration-workflow/rule-delivery.md`). **This file is the rule,
93
- not the hook** — a session that runs no hooks still owes the read.
76
+ **`pnpm josh rule:guard` refuses the body-only read** (`prompts/collaboration-workflow/rule-delivery.md`).
77
+ **This file is the rule, not the hook** — a session without hooks still owes the read.
94
78
 
95
79
  ## A person's update mid-run
96
80
 
97
- When the hook, `review:attest --check` or `followup` shows an Issue update, read it as above — the
98
- later text is in force — fix what it changes, then `pnpm josh issue:ack <N>`. The watch and what it
99
- does not catch: `docs/josh-commands-backlog.md` → "`josh issue:ack`".
81
+ When the hook, `review:attest --check` or `followup` shows an Issue update, read it as above, fix what it
82
+ changes, then `pnpm josh issue:ack <N>`. The watch: `docs/josh-commands-backlog.md` → "`josh issue:ack`".
@@ -1,92 +1,83 @@
1
1
  # `kickoff` — Planning phase only (plan → Issue → Telegram notify → stop)
2
2
 
3
3
  - `kickoff #<N>`: **First `pnpm josh run:entry <N> --to kickoff`** (`docs/how-to/run-issues.md`) — it claims
4
- nothing and prints the stage line alone; `start: reached` means the Issue is already planned or further
5
- up the ladder, so report the stage line and **stop**. Otherwise read existing Issue #N **and every comment on it** — `pnpm josh issue:read <N>`; a
6
- decision recorded after the body was written lives only in a comment, and the later text is the
7
- agreement in force (`issue-comments.md`, which also carries the two answers that stop the run instead) →
8
- **normalize the title**: if the title is not in English or can be phrased more clearly, derive a
9
- better English title and run `gh api -X PATCH repos/{owner}/{repo}/issues/<N> -f title="<title>"` →
10
- analyze requirements → **scope assessment per `split-assessment.md`** → post the plan to the Issue (if
11
- body is blank, `gh api -X PATCH repos/{owner}/{repo}/issues/<N> -f body="<plan>"`; otherwise
12
- `pnpm josh issue:comment <N> --body-file <path>`) → **apply the `run:planned` label** — the mark the next
13
- command's `run:entry` reads to start at the implementation, provisioned by `josh sync` (`gh api
14
- repos/{owner}/{repo}/issues/<N>/labels -f 'labels[]=run:planned' --silent`) → send Telegram
15
- notification, its last line `Next: halfrun #<N> | prrun #<N> | fullrun #<N>` → **stop**
16
- (do not implement). **When the assessment finds two or more separately-mergeable deliverables**, take
17
- the split path instead of posting a plan: create the children as in `kickoff new`, then either
18
- **promote `#N`** with `pnpm josh epic --promote <N> <N1> <N2> ... [--ordered] [--rationale-file
19
- <path|->]` — the right choice when `#N` is a request, a discussion or a container — or, when `#N` is
20
- itself one of the deliverables, keep `#N` as a child and create a new epic with `pnpm josh epic`. That
21
- branch is Tier A: choose it and record the reasoning on the Issue without asking. Present `backlogrun #<E> --only` and stop. Plan comments are written in the session language (`JOSH_SESSION_LANG`, default `ja`).
22
- Telegram notification: `pnpm josh notify --task-type planning --issue-url "<issue-url>" --body=$'-
23
- <bullet1>\n- <bullet2>\n...'`. `--task-type` controls the header icon (`planning` 📋 / `completion` ✅
24
- / `failure` ❌ / `kickoff_retry` 🔄 / `confirmation` ⏸️). `--repo-name` and `--issue-title` are
25
- auto-fetched from `gh` when not supplied. The Issue URL must be included.
4
+ nothing and prints the stage line alone; on `start: reached` report the stage line and **stop**. Then:
5
+ 1. Read Issue #N **and every comment on it** — `pnpm josh issue:read <N>`; the later text is the
6
+ agreement in force (`issue-comments.md`, which also carries the answers that stop the run).
7
+ 2. **Normalize the title** to clear English: `gh api -X PATCH repos/{owner}/{repo}/issues/<N> -f title="<title>"`.
8
+ 3. Analyze requirements → **scope assessment per `split-assessment.md`**.
9
+ 4. Post the plan — a blank body takes `gh api -X PATCH repos/{owner}/{repo}/issues/<N> -f body="<plan>"`,
10
+ otherwise `pnpm josh issue:comment <N> --body-file <path>` — in the session language
11
+ (`JOSH_SESSION_LANG`, default `ja`).
12
+ 5. **Apply the `run:planned` label** — the next command's `run:entry` starts at the implementation
13
+ (`gh api repos/{owner}/{repo}/issues/<N>/labels -f 'labels[]=run:planned' --silent`).
14
+ 6. Send the Telegram notification, its last line `Next: halfrun #<N> | prrun #<N> | fullrun #<N>` →
15
+ **stop** (do not implement).
16
+
17
+ **Two or more separately-mergeable deliverables** take the split path instead of a plan: create the
18
+ children as in `kickoff new`, then either **promote `#N`** with `pnpm josh epic --promote <N> <N1> <N2>
19
+ ... [--ordered] [--rationale-file <path|->]` (when `#N` is a request, a discussion or a container), or
20
+ keep `#N` as a child and create a new epic with `pnpm josh epic`. That branch is Tier A: choose and
21
+ record the reasoning on the Issue. Present `backlogrun #<E> --only` and stop.
22
+
23
+ Telegram: `pnpm josh notify --task-type planning --issue-url "<issue-url>" --body=$'-
24
+ <bullet1>\n- <bullet2>\n...'`. `--task-type` sets the icon (`planning` 📋 / `completion` ✅ /
25
+ `failure` ❌ / `kickoff_retry` 🔄 / `confirmation` ⏸️); `--repo-name` and `--issue-title` are
26
+ auto-fetched. The Issue URL must be included.
26
27
 
27
28
  **`kickoff` does not claim the working-tree hold, and does not release one** — it touches GitHub, never
28
- the tree. `working-tree-hold.md` is the single source.
29
+ the tree (`working-tree-hold.md`).
29
30
 
30
31
  **The target repository is named in front of the Issue reference** — `kickoff kit#new`,
31
- `kickoff joshuafolkken/kit#<N>`. The definition is `target-repository.md`. `kickoff` is the entry that needs
32
- no checkout: name the target repository in the path of every `gh api` call — reads included — and never
33
- clone. The one exception is the split path's epic, since `pnpm josh epic` writes only the repository it
34
- runs in — and the promote arm has no remote fallback at all, so it stops when that repository is not
35
- checked out here. A target whose owner is not this session's is third-party: Tier C, so it stops rather
36
- than filing.
32
+ `kickoff joshuafolkken/kit#<N>` (`target-repository.md`). `kickoff` needs no checkout: name the target in
33
+ every `gh api` path, reads included, and never clone. The exception is the split path's epic — `pnpm josh
34
+ epic` writes only the repository it runs in, and the promote arm stops when that repository is not
35
+ checked out here. A third-party owner is Tier C: stop rather than file.
37
36
 
38
37
  **Read `split-assessment.md` → "The question" first** — `kickoff #N` assesses scope exactly as
39
- `kickoff new` does. Its default is not to split: separability and a scope that clearly exceeds what one
40
- verification gate can confirm in one pass have to hold **together**. The rest of `split-assessment.md`
41
- is read on demand when a split is found.
38
+ `kickoff new` does. The default is not to split: separability and a scope clearly over one verification
39
+ gate must hold **together**. The rest of `split-assessment.md` is read when a split is found.
40
+
41
+ - `kickoff new` or `kickoff new "<title>"`: (0) **Scope assessment** per `split-assessment.md` — one
42
+ deliverable takes the **single-issue path**, several the **multi-issue split path**.
43
+ - **Single-issue path**: (1) Derive an English title, or use the one given. (2) `pnpm josh issue:file
44
+ "<title>" --body-file <body-file> --depth <n>` plus the labels the words typed after `new` name
45
+ ("Words typed after `new`", below; body per `prompts/collaboration-workflow/issue-template.md`) —
46
+ its duplicate scan runs first, and a candidate covering the same work stops the run (`SKILL.md` →
47
+ `issue-scout.md`). Capture `<N>`. (3) Post the plan as `kickoff #<N>` does. (4) Telegram. (5)
48
+ **Stop**.
49
+ - **Multi-issue split path**: (1) Per deliverable, `pnpm josh issue:file "<sub-title>" --body-file
50
+ <body-file> --depth <n> --route split` plus the labels the words after `new` name (duplicate scan
51
+ per `issue-scout.md`). A split filed into another repository gives every child body the `## Origin`
52
+ backlink, the epic the same link as prose (never a checkbox row, which disables its auto-close), and
53
+ the originating Issue lists children and epic under `## Upstream issues`. (2) **Epic — always, for
54
+ every split into two or more Issues**: `pnpm josh epic "<epic-title>" <N1> <N2> ... [--ordered]
55
+ [--rationale-file <path|->] [--origin <owner/repo#N>]`, capturing `<E>`. It builds the `epic` label,
56
+ the task-list rows (`- [ ] #N`), the machine-readable `Dependencies` and the `backlogrun` line; check
57
+ a hand-edited epic with `pnpm josh epic:check <E>`. (3) Telegram listing every created Issue. (4)
58
+ Present `backlogrun #<E> --only`. (5) **Stop**.
59
+
60
+ **The epic itself is never implemented** — `backlogrun` runs its *children*, and `pnpm josh followup`
61
+ closes it once every child is closed. Children with no required order take `None — the children are
62
+ independent; any execution order works.` under `Dependencies`. **Only when the execution order
63
+ matters** (`execution-waves.md` → "When a wave may be declared") pass `--ordered`, which treats the
64
+ argument order as the dependency order.
42
65
 
43
- - `kickoff new` or `kickoff new "<title>"`: No Issue exists yet. Steps: (0) **Scope assessment** per
44
- `split-assessment.md`. If multiple → the **multi-issue split path**; if single → the **single-issue
45
- path**. **Single-issue path**: (1) Derive an English title from the conversation, or use the provided
46
- title. (2) Create Issue: `pnpm josh issue:file "<title>" --body-file <body-file> --depth <n>` plus the labels the words typed after `new` name ("Words typed after `new`", below) (body
47
- per `prompts/collaboration-workflow/issue-template.md`) — its duplicate scan runs first, and a
48
- candidate that covers the same work stops the run rather than filing a second Issue (`SKILL.md` →
49
- `issue-scout.md`). Capture `<N>`. (3)
50
- Post the plan in the session language, using the same body/comment logic as `kickoff #<N>`. (4) Send
51
- Telegram notification. (5) **Stop** — do not implement. **Multi-issue split path**: (1) For each
52
- independent deliverable, derive a focused English title and create a separate Issue with the
53
- `route:split` label (its duplicate scan is read per `issue-scout.md`): `pnpm josh issue:file
54
- "<sub-title>" --body-file <body-file> --depth <n> --route split` plus the labels the words typed after `new` name. Capture each Issue number. **When the split is filed into a repository other than
55
- the one this session is running in**, every child body gets the `## Origin` backlink described in the
56
- cross-package rule the AI documents keep resident, the epic body carries the same link as prose or a
57
- plain bullet (never as a checkbox row, which would disable its auto-close), and the originating Issue
58
- lists the children and the epic under `## Upstream issues`. (2) **Epic — always, for every split into
59
- two or more Issues.** There is no count or ordering condition. **Create it with `pnpm josh epic
60
- "<epic-title>" <N1> <N2> ... [--ordered] [--rationale-file <path|->] [--origin <owner/repo#N>]`**,
61
- capturing its number `<E>` from the printed URL. The command satisfies the epic's four mechanical
62
- requirements by construction — the `epic` label, the task-list rows (`- [ ] #N`), the machine-readable
63
- `Dependencies`, and the printed `backlogrun` line. Check an epic you wrote or edited by hand with `pnpm
64
- josh epic:check <E>`. Only where `josh` is unavailable, fall back to the manual procedure: ensure the
65
- label exists (`gh api repos/{owner}/{repo}/labels -f name=epic -f color=5319e7 -f description="Tracks
66
- a batch of child issues from one split" --silent 2>/dev/null || true`), then create the epic with `gh
67
- api repos/{owner}/{repo}/issues -f title="<epic-title>" -f 'labels[]=epic' -F body=@<body-file>`. Its body
68
- follows the epic format in `prompts/collaboration-workflow/issue-template.md` — split rationale,
69
- dependencies, the `backlogrun` command, and a child task list in task-list syntax (`- [ ] #N`). The epic
70
- exists as the **non-closing home for the split rationale**. When the children have no required order,
71
- write `None — the children are independent; any execution order works.` under `Dependencies`. **The
72
- epic itself is never implemented** — a `backlogrun` takes a named epic and runs its *children*. `pnpm josh
73
- followup` closes it automatically once every child is closed. **Only when the execution order
74
- matters** — the criterion is `execution-waves.md` → "When a wave may be declared" — record it natively: `pnpm josh epic --ordered` treats the argument order as the dependency
75
- order; on the manual fallback path, after the child Issues exist, `gh api
76
- repos/{owner}/{repo}/issues/<N2>/dependencies/blocked_by -F issue_id="$(gh api
77
- repos/{owner}/{repo}/issues/<N1> --jq .id)"` for each dependent pair (the endpoint takes the blocker's
78
- **database id**, not its issue number; a failure here is non-fatal). Never fold the relation into the
79
- creation call. (3) Send Telegram notification listing all created issues. (4) Present the command
80
- `backlogrun #<E> --only`. (5) **Stop** — do not implement.
66
+ **Only where `josh` is unavailable**, the manual fallback: `gh api repos/{owner}/{repo}/labels -f
67
+ name=epic -f color=5319e7 -f description="Tracks a batch of child issues from one split" --silent
68
+ 2>/dev/null || true`, then `gh api repos/{owner}/{repo}/issues -f title="<epic-title>" -f
69
+ 'labels[]=epic' -F body=@<body-file>` with the epic format of `issue-template.md`; an order is
70
+ recorded per pair with `gh api repos/{owner}/{repo}/issues/<N2>/dependencies/blocked_by -F
71
+ issue_id="$(gh api repos/{owner}/{repo}/issues/<N1> --jq .id)"` (the blocker's **database id**; a
72
+ failure is non-fatal), never folded into the creation call.
81
73
 
82
- `pnpm josh issue:file` lints the body and applies the classification labels it declares, following `prompts/collaboration-workflow/issue-template.md` for classification (`docs/josh-commands-backlog.md` → `josh issue:file`).
74
+ `pnpm josh issue:file` lints the body and applies the classification labels it declares (`issue-template.md`; `docs/josh-commands-backlog.md` → `josh issue:file`).
83
75
  An Issue a consumer can use only once it is published is filed with `--release` (`kickoff new`), or linked with `pnpm josh issue:release <N>` (`kickoff #N`) — either makes it a blocker of the repository's `release` Issue, which never gets `auto-ok` on its own.
84
76
 
85
77
  ## Words typed after `new`
86
78
 
87
- **`auto-ok` is judged by `pnpm josh issue:file`, never typed** — by the same criteria as every
88
- filing: the excluded labels and the body's `- 人の判断:` declaration, and a `不要` declaration also needs a run label
89
- (`issue-template.md`).
79
+ **`auto-ok` is judged by `pnpm josh issue:file`, never typed** — the excluded labels and the body's
80
+ `- 人の判断:` declaration; a `不要` declaration also needs a run label (`issue-template.md`).
90
81
  `auto ok` typed after `new` adds nothing.
91
82
 
92
83
  **Words after `new`** (`kickoff new high`) are read like `into <target>`, never inferred. Each adds its
@@ -1,44 +1,34 @@
1
1
  # The observation filing procedure
2
2
 
3
- **Read when an observation turns up — not at the entry.** `SKILL.md` → §2's
4
- table points here for the rule itself: who is asked before a filing, the depth test, what the test
5
- turns away, and carrying the run on. This file is that rule, the depth table, the `issue:file` flags
6
- and what a delegated child does instead. **An observation the depth test turns away, and the kind of miss behind a
7
- user-reported bug, are recorded by `observation-ledger.md` — read it only then**, in the turn that
8
- appends.
9
-
10
- **An unattended run files without asking; an interactive session asks first.** Unattended is a session kit launched under `claude -p` (a lane child, a woken session), a dispatched
11
- lane child, or the `backlogrun` parent — nobody is there to answer, so an offer to file is sent back
12
- by the `Stop` hook. In an interactive session, propose the Issue and file it
13
- once the user confirms; the hook lets the offer through. A current-turn instruction to file, and a
14
- typed command whose own procedure files (a split, a prerequisite, an upstream interrupt), are that
15
- confirmation already.
3
+ **Read when an observation turns up — not at the entry.** `SKILL.md` → §2's table points here. **An
4
+ observation the depth test turns away, and the kind of miss behind a user-reported bug, are recorded by
5
+ `observation-ledger.md` — read it only then**, in the turn that appends.
6
+
7
+ **An unattended run files without asking; an interactive session asks first.** Unattended means a
8
+ `claude -p` session (a lane child, a woken session), a dispatched lane child, or the `backlogrun`
9
+ parent; the `Stop` hook sends an offer to file back. Interactively, propose the Issue and file it
10
+ once the user confirms. A current-turn instruction to file, or a typed command whose procedure files (a
11
+ split, a prerequisite, an upstream interrupt), is that confirmation already.
16
12
 
17
13
  **The trigger is the judgement, not the run's progress** — an ended run, a `kickoff` and a mid-talk
18
14
  turn all file or propose.
19
15
 
20
- **An unattended run that judges something worth filing files it, and does not ask.** An upstream defect stops the
21
- run, a split replaces it, and a prerequisite goes in front of it (`prerequisite.md`). An ordinary
22
- observation changes none of those: it carries no `route:` label, causes no stash or park, and the run
23
- continues. A first-party target is Tier A, decided by `pnpm josh repo:party`; a third-party target is
24
- Tier C (`CLAUDE.md`). Name what was filed in the completion report. An observation nobody would act
25
- on is dropped rather than filed.
16
+ **An unattended run that judges something worth filing files it, and does not ask.** An ordinary
17
+ observation carries no `route:` label, causes no stash or park, and the run continues (unlike an
18
+ upstream defect, a split or a prerequisite — `prerequisite.md`). First-party target: Tier A, by
19
+ `pnpm josh repo:party`; third-party: Tier C (`CLAUDE.md`). Name what was filed in the completion
20
+ report. Drop an observation nobody would act on.
26
21
 
27
22
  **Below the filing bar, a line that could still change a person's judgement is a board note**:
28
23
  `pnpm josh run:event --append note "#<N> <text>"`, shown by `pnpm josh run:board`
29
24
  (`docs/josh-commands-run.md` → "`josh run:board`").
30
25
 
31
- **The filing ceilings still apply.** Count this filing in the ten-Issue limit for the run. An
32
- observation is discretionary, so above the WIP cap in the target repository, close one first or do
33
- not file (`prompts/collaboration-workflow/wip-cap.md`). File it with `pnpm josh issue:file`
34
- (`issue-scout.md`), which lints the body against `prompts/collaboration-workflow/issue-template.md`,
35
- applies the classification labels it declares, runs the duplicate scan, and runs `epic:bundle` on the
36
- new Issue so it is offered by its epic; an `auto-ok` epic adds it to the backlog pool
37
- (`backlogrun-steps.md` → "What one invocation approves"). When it is the second filing of the run, the
38
- command asks the fold question itself and holds a `fold`
39
- (`split-assessment.md` → "The same two questions decide the filing-time fold").
40
-
41
- The marker suite pins the rules below.
26
+ **The filing ceilings still apply.** Count it in the run's ten-Issue limit; above the target
27
+ repository's WIP cap, close one first or do not file (`prompts/collaboration-workflow/wip-cap.md`).
28
+ File with `pnpm josh issue:file` (`issue-scout.md`): it lints the body, applies the classification
29
+ labels, scans for duplicates and runs `epic:bundle` (an `auto-ok` epic adds it to the backlog pool —
30
+ `backlogrun-steps.md` → "What one invocation approves"). On the second filing of the run it asks the fold
31
+ question and holds a `fold` (`split-assessment.md` → "The same two questions decide the filing-time fold").
42
32
 
43
33
  ### The depth test — a discretionary filing cites the product work it blocked
44
34
 
@@ -51,78 +41,49 @@ The marker suite pins the rules below.
51
41
  | **2** | What measures a run | `josh cost` and the run-timing report |
52
42
 
53
43
  **The depth is recorded on the Issue as a label, and the label is applied when the Issue is filed.**
54
- `depth:0`, `depth:1` and `depth:2` are the three, defined once in
55
- `scripts/issue/issue-labels.ts` and carrying no definition of their own — **the table above is the
56
- single source**, and a label description that paraphrased it would be a second copy of the rule.
57
- **Every filing route applies one**, this route and the other three of `prerequisite.md`'s table alike: a `new`
58
- entry point, a `route:tier-a` prerequisite, a `route:interrupt`, a split child and a review round
59
- cap's branch-2 filing all pass through a `pnpm josh issue:file` call, and the depth goes in it as
60
- `--depth <n>` beside whatever `--route` that call already carries.
44
+ `depth:0` / `depth:1` / `depth:2` are defined in `scripts/issue/issue-labels.ts` with no definition of
45
+ their own — **the table above is the single source**. **Every filing route applies one**: each route
46
+ of `prerequisite.md`'s table, a split child and a review branch-2 filing pass `--depth <n>` to
47
+ `pnpm josh issue:file`, beside any `--route`.
61
48
 
62
49
  ```bash
63
50
  pnpm josh issue:file "<title>" --body-file <body-file> --depth 1
64
51
  gh api repos/{owner}/{repo}/issues/<N>/labels -f 'labels[]=depth:1' # an Issue already filed
65
52
  ```
66
53
 
67
- **A repository missing the three gets them from `issue:file` itself** — it creates any missing
68
- workflow label, with the color and description `DEPTH_LABELS` in `scripts/issue/issue-labels.ts`
69
- defines, before the create call.
54
+ `issue:file` creates any missing workflow label from `DEPTH_LABELS` before the create call.
70
55
 
71
- - **It is read off the subject, exactly as the table is** — so applying it is not a judgement and not
72
- a person's to make, which is what separates it from `auto-ok` and `needs-human-review`. Those two
73
- decide what a run may do (`auto-ok` by `issue:file`'s judgement against the criteria —
74
- `backlogrun-steps.md` → "What one invocation approves"); this one records what an Issue is about
75
- and withholds nothing.
56
+ - **It is read off the subject, exactly as the table is** — not a judgement, unlike `auto-ok` and
57
+ `needs-human-review`; it withholds nothing.
76
58
  - **Applied at filing, not at completion.**
77
- - **An Issue carrying more than one counts as the lowest depth present**, the one closest to the
78
- consumer.
79
- - **An `epic` takes no depth label**, because it has no subject of its own to read one off — its
80
- children carry the subjects, and the share below excludes it from the denominator for that same
81
- reason.
59
+ - **An Issue carrying more than one counts as the lowest depth present.**
60
+ - **An `epic` takes no depth label** and is excluded from the share's denominator.
82
61
 
83
62
  Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why the depth label is applied at filing".
84
63
 
85
64
  - **A discretionary observation at depth 1 or deeper is filed only where it can cite the depth-0 work
86
- it stopped or delayed** — named as an Issue number or a run, never as "this would slow runs down".
87
- **Cannot cite one, it is not filed**: it goes to the ledger (`observation-ledger.md`), and what files it later is
88
- either the blockage arriving or a second sighting of the same thing. Pull rather than push — the
89
- fix follows the jam or the repeat, never the lone sighting.
90
- - **A depth-0 observation does not take this test.** That is the product, and the two ceilings above
91
- stay its only limits.
92
- - **`route:tier-a` and `route:interrupt` do not take it either**, at any depth: a filing the run
93
- cannot proceed without is already citing its own blockage.
94
- - **A depth-2 filing — one whose subject is what measures a run — carries a further requirement, on
95
- top of the depth-0 citation above rather than in place of it.** A
96
- discretionary depth-2 filing states two things the depth-0 citation does not force:
97
- - **The decision the number would change, named** — the Issue number holding the choice it is
98
- waiting on, or a decision a person is about to make. "Slow", "large" and "worth knowing" are not a
99
- decision.
100
- - **Which way it tips** — what range of the number selects which choice. A number that selects the
101
- same action whatever it turns out to be changes no decision, and a filing that cannot write this
102
- line is describing one.
103
- - **Cannot write both, it is not filed** — the same exit the depth-0 gate takes: the ledger,
104
- pulled into an Issue by the jam arriving or the second sighting, never pushed by the lone idea.
105
- - **This narrows depth 2 alone, and the exemptions above carry over unchanged.** `route:tier-a` and
106
- `route:interrupt` do not take this requirement any more than they take the depth-0 citation, a
107
- depth-0 observation does not take it because it is the product, and a review round cap's branch-2
108
- filing (below) clears its own bar and never reaches this one.
65
+ it stopped or delayed** — an Issue number or a run, never "this would slow runs down". **Cannot cite
66
+ one, it is not filed**: it goes to the ledger (`observation-ledger.md`); the blockage arriving or a
67
+ second sighting files it later.
68
+ - **A depth-0 observation does not take this test**; the two ceilings are its only limits.
69
+ - **`route:tier-a` and `route:interrupt` do not take it either**, at any depth.
70
+ - **A depth-2 filing also states, on top of the depth-0 citation:**
71
+ - **The decision the number would change, named** — the Issue holding the choice, or a decision a
72
+ person is about to make. "Slow", "large" and "worth knowing" are not a decision.
73
+ - **Which way it tips** — what range of the number selects which choice.
74
+ - **Cannot write both, it is not filed** — it goes to the ledger.
75
+ - **This narrows depth 2 alone, and the exemptions above carry over unchanged.**
109
76
 
110
77
  Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why depth gates a discretionary filing".
111
78
 
112
- **It governs this route only — the fourth row of `prerequisite.md`'s table.** A review finding routed to branch 2
113
- of `prompts/review.md` → "Review round cap" is filed under that section's own bar — a confirmed
114
- defect reaching a runtime path, with a written failure scenario — and **does not take the depth
115
- test**: it has already cleared a bar this route has not, so gating it on a citation as well would
116
- drop the one kind of finding both documents agree is never dropped. **That bar is the reason, and the
117
- subject's depth is not.** Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why a
118
- review branch-2 filing skips the depth test".
119
-
120
- **And a PR that *adds* a measurement names its reader in the same way.** The requirement above binds
121
- a depth-2 Issue that *proposes* a measurement; a pull request that *adds* one — a new report column,
122
- section, scope or subcommand, a diagnostic step — states in its body the reader that consumes it: the
123
- Issue number that read the value to decide something, or the path of the rule that reads it. **A
124
- measurement with no reader is not added.** `route:tier-a` and
125
- `route:interrupt` carry over unchanged.
79
+ **It governs this route only — the fourth row of `prerequisite.md`'s table.** A review finding routed
80
+ to branch 2 of `prompts/review.md` → "Review round cap" is filed under that section's own bar and
81
+ **does not take the depth test**. **That bar is the reason, and the subject's depth is not.**
82
+ Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why a review branch-2 filing skips the depth test".
83
+
84
+ **And a PR that *adds* a measurement names its reader in the same way** — the Issue that read the value
85
+ to decide something, or the path of the rule that reads it. **A measurement with no reader is not
86
+ added.** `route:tier-a` and `route:interrupt` carry over unchanged.
126
87
 
127
88
  ### The depth-0 share — what is counted
128
89
 
@@ -131,38 +92,32 @@ measurement with no reader is not added.** `route:tier-a` and
131
92
  **The denominator is a rule, not a choice, and this is it:**
132
93
 
133
94
  - **Counted: every open Issue that does not carry `epic`.**
134
- - **`route:tier-a` and `route:interrupt` are counted like anything else.** The depth test above
135
- exempts them from its *citation* requirement; it never said they are not work.
95
+ - **`route:tier-a` and `route:interrupt` are counted like anything else.**
136
96
  - **An Issue with no depth label is in the denominator**, counted separately as `unlabelled`.
137
97
  - **The numerator is what is left**: open, non-epic Issues carrying `depth:0`.
138
98
 
139
- **Two readings of the same backlog give the same number**: nothing in the count is left to the
140
- counter's judgement.
99
+ **Two readings of the same backlog give the same number.**
141
100
 
142
101
  Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why the depth-0 denominator is fixed".
143
102
 
144
- **What the number is for is not decided here.** Changing what `backlog:next` offers on the strength
145
- of it, and setting a target value, are both out of scope until the current value has
146
- been measured the same way more than once.
103
+ **What the number is for is not decided here** — no `backlog:next` change and no target value until it
104
+ has been measured the same way more than once.
147
105
 
148
106
  ### A delegated child does not take this route
149
107
 
150
- **A delegated child files `route:tier-a` and `route:interrupt` only.** Its discretionary
151
- observations are not filed by the child at all: they go back in the summary's "Observations that
152
- could bite later" line (`backlogrun-child.md` → "What the summary carries, and how long it may be"), and the
153
- parent files what survives — under the depth test above, and inside the run's ceiling.
108
+ **A delegated child files `route:tier-a` and `route:interrupt` only.** Its discretionary observations
109
+ go in the summary's "Observations that could bite later" line (`backlogrun-child.md` → "What the
110
+ summary carries, and how long it may be"); the parent files what survives the depth test, inside the
111
+ run's ceiling.
154
112
 
155
113
  **A delegated child does not append to the ledger either — the parent collapses the duplicates and
156
- appends what is left.** The child's only route is the summary's "Observations that could bite later"
157
- line; the parent chooses the key, checks the count and writes the line. **The 10-per-run ceiling for this route is the parent's to
158
- count.** **Lines its own `review:record` and `measure:rerun` write are not this route** — they go to
159
- its issue's file in its lane (`observation-ledger.md` → "The ledger — where an observation that
160
- cannot cite a blockage goes").
114
+ appends what is left.** **The 10-per-run ceiling for this route is the parent's to count.** **Lines
115
+ its own `review:record` and `measure:rerun` write are not this route** — they go to its issue's file in
116
+ its lane (`observation-ledger.md` → "The ledger — where an observation that cannot cite a blockage goes").
161
117
 
162
- Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why a delegated child neither files
163
- nor appends".
118
+ Rationale: `docs/maintainers/observation-filing-rationale.md` → "Why a delegated child neither files nor appends".
164
119
 
165
- **This file is the single source of every procedure above**, and `SKILL.md` → §2's table carries the
166
- trigger of the rule they carry out; nothing under `prompts/collaboration-workflow/` restates either.
120
+ **This file is the single source of every procedure above**; nothing under
121
+ `prompts/collaboration-workflow/` restates it.
167
122
 
168
123
  Provenance: `docs/maintainers/observation-filing-rationale.md` → "Where each rule came from".