dev-loops 0.1.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 (156) hide show
  1. package/.pi/dev-loop/defaults.yaml +477 -0
  2. package/AGENTS.md +25 -0
  3. package/CHANGELOG.md +18 -0
  4. package/LICENSE +21 -0
  5. package/README.md +178 -0
  6. package/agents/dev-loop.agent.md +82 -0
  7. package/agents/developer.agent.md +37 -0
  8. package/agents/docs.agent.md +33 -0
  9. package/agents/fixer.agent.md +53 -0
  10. package/agents/quality.agent.md +28 -0
  11. package/agents/refiner.agent.md +87 -0
  12. package/agents/review.agent.md +64 -0
  13. package/cli/index.mjs +424 -0
  14. package/extension/README.md +233 -0
  15. package/extension/checks.ts +94 -0
  16. package/extension/index.ts +131 -0
  17. package/extension/post-merge-update.ts +512 -0
  18. package/extension/presentation.ts +107 -0
  19. package/lib/dev-loops-core.mjs +284 -0
  20. package/package.json +103 -0
  21. package/scripts/README.md +1007 -0
  22. package/scripts/_cli-primitives.mjs +10 -0
  23. package/scripts/_core-helpers.mjs +30 -0
  24. package/scripts/docs/validate-links.mjs +567 -0
  25. package/scripts/docs/validate-no-duplicate-rules.mjs +250 -0
  26. package/scripts/github/_review-thread-mutations.mjs +214 -0
  27. package/scripts/github/capture-review-threads.mjs +180 -0
  28. package/scripts/github/create-draft-pr.mjs +108 -0
  29. package/scripts/github/detect-checkpoint-evidence.mjs +393 -0
  30. package/scripts/github/detect-linked-issue-pr.mjs +331 -0
  31. package/scripts/github/manage-sub-issues.mjs +394 -0
  32. package/scripts/github/probe-copilot-review.mjs +323 -0
  33. package/scripts/github/ready-for-review.mjs +93 -0
  34. package/scripts/github/reconcile-draft-gate.mjs +328 -0
  35. package/scripts/github/reply-resolve-review-thread.mjs +42 -0
  36. package/scripts/github/reply-resolve-review-threads.mjs +329 -0
  37. package/scripts/github/request-copilot-review.mjs +551 -0
  38. package/scripts/github/resolve-tracker-local-spec.mjs +205 -0
  39. package/scripts/github/stage-reviewer-draft.mjs +191 -0
  40. package/scripts/github/upsert-checkpoint-verdict.mjs +694 -0
  41. package/scripts/github/verify-fresh-review-context.mjs +125 -0
  42. package/scripts/github/write-gate-findings-log.mjs +212 -0
  43. package/scripts/loop/_checkpoint-io.mjs +55 -0
  44. package/scripts/loop/_checkpoint-paths.mjs +28 -0
  45. package/scripts/loop/_handoff-contract.mjs +230 -0
  46. package/scripts/loop/_inspect-run-viewer-adapter.mjs +345 -0
  47. package/scripts/loop/_loop-evidence.mjs +32 -0
  48. package/scripts/loop/_pr-runner-coordination.mjs +611 -0
  49. package/scripts/loop/_stale-runner-detection.mjs +145 -0
  50. package/scripts/loop/_steering-state-file.mjs +134 -0
  51. package/scripts/loop/build-handoff-envelope.mjs +181 -0
  52. package/scripts/loop/checkpoint-contract.mjs +49 -0
  53. package/scripts/loop/conductor-monitor.mjs +1850 -0
  54. package/scripts/loop/conductor.mjs +214 -0
  55. package/scripts/loop/copilot-pr-handoff.mjs +493 -0
  56. package/scripts/loop/debt-remediate.mjs +304 -0
  57. package/scripts/loop/detect-change-scope.mjs +102 -0
  58. package/scripts/loop/detect-copilot-loop-state.mjs +454 -0
  59. package/scripts/loop/detect-copilot-session-activity.mjs +186 -0
  60. package/scripts/loop/detect-initial-copilot-pr-state.mjs +318 -0
  61. package/scripts/loop/detect-internal-only-pr.mjs +270 -0
  62. package/scripts/loop/detect-issue-refinement-artifact.mjs +163 -0
  63. package/scripts/loop/detect-pr-gate-coordination-state.mjs +509 -0
  64. package/scripts/loop/detect-reviewer-loop-state.mjs +231 -0
  65. package/scripts/loop/detect-stale-runner.mjs +250 -0
  66. package/scripts/loop/detect-tracker-first-loop-state.mjs +76 -0
  67. package/scripts/loop/detect-tracker-pr-state.mjs +102 -0
  68. package/scripts/loop/info.mjs +267 -0
  69. package/scripts/loop/inspect-run-viewer/cli.mjs +117 -0
  70. package/scripts/loop/inspect-run-viewer/constants.mjs +80 -0
  71. package/scripts/loop/inspect-run-viewer/graph.mjs +757 -0
  72. package/scripts/loop/inspect-run-viewer/handoff-envelope-renderer.mjs +398 -0
  73. package/scripts/loop/inspect-run-viewer/inbox.mjs +308 -0
  74. package/scripts/loop/inspect-run-viewer/managed-instance.mjs +750 -0
  75. package/scripts/loop/inspect-run-viewer/rendering.mjs +411 -0
  76. package/scripts/loop/inspect-run-viewer/server.mjs +638 -0
  77. package/scripts/loop/inspect-run-viewer/shared.mjs +103 -0
  78. package/scripts/loop/inspect-run-viewer/status.mjs +715 -0
  79. package/scripts/loop/inspect-run-viewer-ci-changes.mjs +77 -0
  80. package/scripts/loop/inspect-run-viewer.mjs +82 -0
  81. package/scripts/loop/inspect-run.mjs +382 -0
  82. package/scripts/loop/outer-loop.mjs +419 -0
  83. package/scripts/loop/pr-runner-coordination.mjs +143 -0
  84. package/scripts/loop/pre-commit-branch-guard.mjs +68 -0
  85. package/scripts/loop/pre-flight-gate.mjs +236 -0
  86. package/scripts/loop/pre-pr-ready-gate.mjs +183 -0
  87. package/scripts/loop/pre-push-main-guard.mjs +103 -0
  88. package/scripts/loop/pre-write-remote-freshness-guard.mjs +32 -0
  89. package/scripts/loop/print-gates.mjs +42 -0
  90. package/scripts/loop/resolve-dev-loop-startup.mjs +533 -0
  91. package/scripts/loop/run-conductor-cycle.mjs +322 -0
  92. package/scripts/loop/run-queue.mjs +124 -0
  93. package/scripts/loop/run-refinement-audit.mjs +513 -0
  94. package/scripts/loop/run-watch-cycle.mjs +358 -0
  95. package/scripts/loop/steer-loop.mjs +841 -0
  96. package/scripts/loop/ui-designer-review-contract.mjs +76 -0
  97. package/scripts/loop/watch-initial-copilot-pr.mjs +253 -0
  98. package/scripts/projects/add-queue-item.mjs +528 -0
  99. package/scripts/projects/ensure-queue-board.mjs +837 -0
  100. package/scripts/projects/list-queue-items.mjs +489 -0
  101. package/scripts/projects/move-queue-item.mjs +549 -0
  102. package/scripts/projects/reorder-queue-item.mjs +518 -0
  103. package/scripts/refine/_refine-helpers.mjs +258 -0
  104. package/scripts/refine/prose-linkage-detector.mjs +92 -0
  105. package/scripts/refine/refinement-completeness-checker.mjs +88 -0
  106. package/scripts/refine/scope-boundary-cross-checker.mjs +163 -0
  107. package/scripts/refine/tree-integrity-validator.mjs +211 -0
  108. package/scripts/refine/verify.mjs +178 -0
  109. package/scripts/repo-wiki-local.mjs +156 -0
  110. package/scripts/repo-wiki.mjs +119 -0
  111. package/skills/copilot-pr-followup/SKILL.md +380 -0
  112. package/skills/dev-loop/SKILL.md +141 -0
  113. package/skills/dev-loop/scripts/dev-mode-context.mjs +152 -0
  114. package/skills/dev-loop/scripts/dev-mode-context.test.mjs +80 -0
  115. package/skills/dev-loop/scripts/init-phase.mjs +71 -0
  116. package/skills/dev-loop/scripts/log-bash-exit-1.mjs +25 -0
  117. package/skills/dev-loop/scripts/phase-files.mjs +29 -0
  118. package/skills/dev-loop/scripts/post-gate-verdict-fallback.mjs +480 -0
  119. package/skills/dev-loop/scripts/post-gate-verdict-fallback.test.mjs +732 -0
  120. package/skills/dev-loop/scripts/render-template.mjs +82 -0
  121. package/skills/dev-loop/scripts/render-template.test.mjs +63 -0
  122. package/skills/dev-loop/templates/bootstrap-agents.md +26 -0
  123. package/skills/dev-loop/templates/bootstrap-implementation-state.md +31 -0
  124. package/skills/dev-loop/templates/bootstrap-implementation-workflow.md +17 -0
  125. package/skills/dev-loop/templates/dev-mode-retrospective.md +15 -0
  126. package/skills/dev-loop/templates/dev-mode-review.md +17 -0
  127. package/skills/dev-loop/templates/dev-mode-skill-changes.md +11 -0
  128. package/skills/dev-loop/templates/merged-phase-plan.md +19 -0
  129. package/skills/dev-loop/templates/phase-doc.md +27 -0
  130. package/skills/dev-loop/templates/phase-summary.md +13 -0
  131. package/skills/dev-loop/templates/phase-variant.md +15 -0
  132. package/skills/dev-loop/templates/retrospective.md +11 -0
  133. package/skills/dev-loop/templates/review.md +32 -0
  134. package/skills/dev-loop/templates/ui-vision-review.md +55 -0
  135. package/skills/docs/acceptance-criteria-verification.md +21 -0
  136. package/skills/docs/anti-patterns.md +21 -0
  137. package/skills/docs/artifact-authority-contract.md +119 -0
  138. package/skills/docs/confirmation-rules.md +28 -0
  139. package/skills/docs/copilot-ci-status-contract.md +52 -0
  140. package/skills/docs/copilot-loop-operations.md +233 -0
  141. package/skills/docs/debt-remediation-contract.md +107 -0
  142. package/skills/docs/entrypoint-strategies.md +115 -0
  143. package/skills/docs/epic-tree-refinement-procedure.md +234 -0
  144. package/skills/docs/issue-intake-procedure.md +235 -0
  145. package/skills/docs/main-agent-contract.md +72 -0
  146. package/skills/docs/merge-preconditions.md +29 -0
  147. package/skills/docs/pr-lifecycle-contract.md +209 -0
  148. package/skills/docs/public-dev-loop-contract.md +497 -0
  149. package/skills/docs/retrospective-checkpoint-contract.md +159 -0
  150. package/skills/docs/stop-conditions.md +29 -0
  151. package/skills/docs/structural-quality.md +42 -0
  152. package/skills/docs/tracker-first-loop-state.md +281 -0
  153. package/skills/docs/validation-policy.md +27 -0
  154. package/skills/docs/workflow-handoff-contract.md +135 -0
  155. package/skills/final-approval/SKILL.md +19 -0
  156. package/skills/local-implementation/SKILL.md +640 -0
@@ -0,0 +1,234 @@
1
+ # Epic tree refinement procedure
2
+
3
+ This document is the canonical procedure for depth-first, top-down-then-bottom-up refinement of
4
+ an existing GitHub sub-issue tree (parent → children → grandchildren).
5
+
6
+ Use it together with:
7
+ - [Issue Intake Procedure](./issue-intake-procedure.md) — Phase 3b calls this procedure for epic decomposition
8
+ - [Sub-Issue Tree Contract](../../docs/sub-issue-tree-contract.md) — authoritative sub-issue tooling (source-repo reference)
9
+
10
+ When you have a tree of GitHub issues that already exists and you need to align AC, DoD, scope
11
+ boundaries, and delegation contracts across all levels, follow this procedure. It is deterministic
12
+ enough that a fresh agent can run it without prior context about the tree.
13
+
14
+ ---
15
+
16
+ ## Definitions
17
+
18
+ | Term | Meaning |
19
+ |---|---|
20
+ | **Root** | The umbrella/epic issue at the top of the tree |
21
+ | **Parent** | Any issue that has at least one sub-issue child |
22
+ | **Child** | A direct sub-issue of a parent |
23
+ | **Leaf** | An issue with no sub-issue children |
24
+ | **Phase table** | A section of the root/parent body that names each child and what it owns vs excludes |
25
+ | **Scope boundary** | Explicit text in an issue body: `"This issue owns X. It does NOT own Y (#NNN)."` |
26
+ | **AC/DoD matrix** | A two-column table mapping each acceptance criterion to its corresponding DoD checklist item(s) |
27
+
28
+ ---
29
+
30
+ ## Prerequisites
31
+
32
+ Before starting, verify:
33
+
34
+ 1. The root issue and all intended children/grandchildren exist as GitHub issues in the repo.
35
+ 2. The sub-issue tree is attached (run `node <resolved-skill-scripts>/github/manage-sub-issues.mjs list --repo <repo> --issue <root>` to inspect it).
36
+ 3. You have the resolved repo slug (`owner/name`).
37
+
38
+ Optional but recommended before and after edits:
39
+
40
+ ```sh
41
+ dev-loops refine verify --issue <root> --repo <repo>
42
+ ```
43
+
44
+ This verification command checks linkage policy, sibling scope boundaries, refinement completeness,
45
+ and tree integrity in one deterministic pass.
46
+
47
+ If the sub-issue tree does not yet exist, use [Issue Intake Procedure](./issue-intake-procedure.md) Phase 3b to decompose and attach it first.
48
+
49
+ ---
50
+
51
+ ## Phases
52
+
53
+ ### Phase A — Root refinement (serial)
54
+
55
+ Refine the root issue **first** before touching any child.
56
+
57
+ For the root issue:
58
+ 1. Read the current body: `gh issue view <root> --repo <repo> --json number,title,body`
59
+ 2. Confirm the problem statement is clear and scoped
60
+ 3. Confirm a **phase scope table** exists — one row per immediate child naming what each child
61
+ owns and what it excludes; add or update this table if missing
62
+ 4. Confirm **AC checklist** covers the end-to-end goal (not the implementation details owned by children)
63
+ 5. Confirm **DoD checklist** — merge-ready condition for the root issue as a whole
64
+ 6. Confirm **AC/DoD matrix** — each AC maps to at least one DoD item
65
+ 7. Confirm **non-goals** section — prevents scope creep into adjacent areas
66
+ 8. Write the updated body to a tmp file: `tmp/issues/<root>/refinement/root-body.md`
67
+ 9. Show the diff and obtain confirmation before mutating GitHub
68
+ 10. Apply: `gh issue edit <root> --repo <repo> --body-file tmp/issues/<root>/refinement/root-body.md`
69
+
70
+ **Gate:** Phase B must not start until Phase A is complete and the root body is updated on GitHub.
71
+
72
+ ---
73
+
74
+ ### Phase B — Descend: refine children against parent (parallel fan-out per level)
75
+
76
+ For **each level** of the tree (breadth-first traversal of levels, depth-first traversal within
77
+ a single branch), refine all siblings in parallel — siblings are independent and only need the
78
+ parent's updated body, not each other's output.
79
+
80
+ **For each issue at this level:**
81
+
82
+ 1. Read the parent's updated body: `gh issue view <parent> --repo <repo> --json number,title,body`
83
+ 2. Read the current child body: `gh issue view <child> --repo <repo> --json number,title,body`
84
+ 3. Verify the child's scope matches what the parent's phase table delegates to it
85
+ 4. Identify any overlap with sibling issues (read sibling titles/bodies if needed)
86
+ 5. Refine the child body with:
87
+ - **Scope boundary** (explicit): `"This issue owns X. It does NOT own Y (#NNN) or Z (#MMM)."`
88
+ - **AC checklist** specific to this child's bounded scope
89
+ - **DoD checklist** — when is this child independently closable?
90
+ - **AC/DoD matrix**
91
+ - **Non-goals** — what this child intentionally excludes
92
+ 6. Write refined body to `tmp/issues/<child>/refinement/child-body.md`
93
+ 7. Show the diff and obtain confirmation before mutating (unless running unattended with explicit authorization)
94
+ 8. Apply: `gh issue edit <child> --repo <repo> --body-file tmp/issues/<child>/refinement/child-body.md`
95
+
96
+ **Parallelism rule:** All siblings at the same level can be refined concurrently. No child needs
97
+ another child's output; each child only reads the parent's contract and its own current body.
98
+
99
+ **Serial gate between levels:** All children at level N must complete before descending to level N+1.
100
+
101
+ Repeat Phase B until all leaves are refined.
102
+
103
+ ---
104
+
105
+ ### Phase C — Ascend: reconcile parents with children (parallel fan-out per level)
106
+
107
+ After all children under a given parent are refined, reconcile that parent. Work bottom-up.
108
+
109
+ All parents at the same depth can be reconciled in parallel (they only need their own children's
110
+ updated bodies, not sibling parents).
111
+
112
+ **For each parent (bottom-up):**
113
+
114
+ 1. Re-read the parent body: `gh issue view <parent> --repo <repo> --json number,title,body`
115
+ 2. Re-read all direct children bodies
116
+ 3. Verify:
117
+ - The parent's phase scope table still matches what the children now claim to own
118
+ - No orphaned responsibilities (parent promised something no child owns)
119
+ - No duplicate ownership (two children claiming the same thing)
120
+ 4. Update the parent's phase scope table and AC/DoD as needed to reflect what children now explicitly own
121
+ 5. Write refined body to `tmp/issues/<parent>/refinement/parent-reconciled-body.md`
122
+ 6. Show the diff and obtain confirmation before mutating
123
+ 7. Apply: `gh issue edit <parent> --repo <repo> --body-file tmp/issues/<parent>/refinement/parent-reconciled-body.md`
124
+
125
+ **Serial gate between levels:** All parents at depth N must complete reconciliation before ascending to depth N-1.
126
+
127
+ ---
128
+
129
+ ### Phase D — Root final reconcile (serial)
130
+
131
+ After all immediate children of the root have been reconciled:
132
+
133
+ 1. Re-read the root body: `gh issue view <root> --repo <repo> --json number,title,body`
134
+ 2. Re-read all immediate children bodies
135
+ 3. Verify:
136
+ - Phase scope table matches actual child scope
137
+ - Dependency chain is correct (does execution order in the sub-issue tree match dependencies?)
138
+ - No orphaned responsibilities; no duplicate ownership
139
+ 4. Update the root body with the final reconciled phase scope table and AC/DoD
140
+ 5. Write to `tmp/issues/<root>/refinement/root-final-body.md`
141
+ 6. Show the diff and obtain confirmation before mutating
142
+ 7. Apply: `gh issue edit <root> --repo <repo> --body-file tmp/issues/<root>/refinement/root-final-body.md`
143
+ 8. Verify the sub-issue tree still reflects the correct execution order:
144
+ ```sh
145
+ node <resolved-skill-scripts>/github/manage-sub-issues.mjs verify \
146
+ --repo <repo> --issue <root> --expected <n1,n2,...> --ordered
147
+ ```
148
+
149
+ **Gate:** Root final reconcile completes the procedure. All issues in the tree must now have:
150
+ - AC checklist, DoD checklist, AC/DoD matrix, non-goals, explicit scope boundary
151
+
152
+ ---
153
+
154
+ ## Rules
155
+
156
+ - **No implementation, no PRs, no Copilot assignment** — this procedure is refinement-only
157
+ - **Use `gh issue edit`** to apply changes directly — do not create new issues or PRs
158
+ - **No prose parent/child links in bodies** — GitHub sub-issues API handles hierarchy
159
+ - **Each issue must have:** AC checklist, DoD checklist, non-goals, AC/DoD matrix, scope boundary
160
+ - **Scope boundary format:** `"This issue owns X. It does NOT own Y (#NNN) or Z (#MMM)."`
161
+ - **Show the diff** and get confirmation before each `gh issue edit` mutation (unless unattended with explicit authorization)
162
+ - **Write tmp artifacts** under `tmp/issues/<number>/refinement/` before applying
163
+ - **Do not duplicate** the child list in parent bodies — the sub-issue tree API owns hierarchy
164
+
165
+ ---
166
+
167
+ ## Parallelism model
168
+
169
+ Sibling refinements are independent: siblings only need the parent's contract, not each other's
170
+ output. The wall-clock complexity is O(depth), not O(nodes).
171
+
172
+ ```text
173
+ Phase A: [root] serial (1 step)
174
+ Phase B: [child1 || child2 || child3] parallel per level (1 step per level)
175
+ [gc1a || gc1b || gc2a || gc3a] parallel per level (1 step per level)
176
+ Phase C: [child1 || child2 || child3] parallel per level (1 step per level)
177
+ Phase D: [root] serial (1 step)
178
+ ```
179
+
180
+ Total serial steps for a tree with depth D: `1 + (D-1) + (D-1) + 1 = 2D`
181
+
182
+ **Fan-out rule:** At any level, when a parent is refined, ALL its children can be refined in parallel.
183
+
184
+ **Serial gates:**
185
+ - Root refinement must complete before any child starts
186
+ - A parent's reconciliation must wait for ALL its children to finish
187
+ - Root reconciliation must wait for all immediate children to reconcile
188
+
189
+ ---
190
+
191
+ ## Completion criteria
192
+
193
+ The procedure is complete when all issues in the tree satisfy:
194
+
195
+ | Check | How to verify |
196
+ |---|---|
197
+ | AC checklist present | Issue body contains `## Acceptance Criteria` with at least one `- [ ]` item |
198
+ | DoD checklist present | Issue body contains `## Definition of Done` with at least one `- [ ]` item |
199
+ | AC/DoD matrix present | Issue body contains a two-column table mapping AC items to DoD items |
200
+ | Non-goals present | Issue body contains `## Non-goals` section |
201
+ | Scope boundary present | Issue body contains explicit `"This issue owns ... It does NOT own ..."` text |
202
+ | No orphaned responsibilities | Each thing the parent delegates maps to exactly one child |
203
+ | No duplicate ownership | No two siblings claim the same responsibility |
204
+ | Sub-issue tree order valid | `manage-sub-issues.mjs verify --ordered` exits 0 |
205
+
206
+ ---
207
+
208
+ ## Example traversal for a 3-level tree
209
+
210
+ For root #715 with children #716, #717, #718 and grandchildren #720–#729:
211
+
212
+ ```
213
+ Phase A: #715 refine
214
+ Phase B level 2 (parallel): #716 refine ‖ #717 refine ‖ #718 refine
215
+ Phase B level 3 (parallel): #720 ‖ #721 ‖ #722 (under #716)
216
+ #723 ‖ #724 (under #717)
217
+ #726 ‖ #729 ‖ #727 ‖ #728 (under #718)
218
+ Phase C level 2 (parallel): #716 reconcile ‖ #717 reconcile ‖ #718 reconcile
219
+ Phase D: #715 root reconcile
220
+ ```
221
+
222
+ Wall-clock serial steps: 5 (not 17).
223
+
224
+ ---
225
+
226
+ ## Relationship to other procedures
227
+
228
+ | Procedure | When to use it |
229
+ |---|---|
230
+ | [Issue Intake Procedure](./issue-intake-procedure.md) Phase 3b | *Creating* a new sub-issue tree from an umbrella issue |
231
+ | **This procedure** | *Refining* an existing sub-issue tree to align scope, AC, DoD, and delegation contracts |
232
+ | [Sub-Issue Tree Contract](../../docs/sub-issue-tree-contract.md) | Tooling for listing, attaching, ordering, and verifying sub-issue trees |
233
+
234
+ These are complementary. Phase 3b creates the structure; this procedure aligns the contracts.
@@ -0,0 +1,235 @@
1
+ # Issue intake procedure
2
+
3
+ This document is the canonical owner of the routed `issue_intake` procedure behind the public `dev-loop` façade.
4
+
5
+ Use it together with:
6
+ - [Copilot PR Follow-up Skill](../copilot-pr-followup/SKILL.md)
7
+ - [Public Dev Loop Contract](./public-dev-loop-contract.md)
8
+ - [Retrospective Checkpoint Contract](./retrospective-checkpoint-contract.md) when the current step depends on async start/resume/status or retrospective enforcement
9
+
10
+ When routed work is issue-first rather than already in active PR follow-up, use the procedure below before entering the shared post-PR loop. Treat this document as the issue-refinement specialist procedure for the routed `issue_intake` seam.
11
+
12
+ ## New-idea safety layer (default contract in this repo)
13
+
14
+ For **all new ideas** that are not already anchored to an existing issue (including abstract ideas such as plain-language requests without an issue number or plan-doc path), apply this procedure-owned intake contract before any GitHub mutation:
15
+
16
+ - procedure owns classification; human operator gates all mutations
17
+ - run classification in fresh context by default
18
+ - run classification asynchronously when practical
19
+ - run async fan-out / fan-in proposal generation by default when practical
20
+ - emit a proposal artifact before any GitHub state-changing mutation, including create/edit/retitle/collapse/link operations
21
+ - default to create-new over overwrite/update when a new tracked artifact is justified
22
+ - do not repurpose/retitle/collapse/overwrite an existing issue unless that exact mutation is explicitly proposed and explicitly approved
23
+ - after approval, run a second async mutation pass (dispatched via the procedure) instead of mutating directly from inherited context
24
+ - verify post-mutation artifact state and record what actually changed
25
+
26
+ Deterministic intake + mutation-gate state machine:
27
+
28
+ ```text
29
+ idea_received
30
+ -> fresh_context_started
31
+ -> fanout_started
32
+ -> fanin_complete
33
+ -> artifact_scan_complete
34
+ -> classified
35
+ -> proposal_emitted
36
+ -> awaiting_user_approval
37
+ -> ready_for_mutation
38
+ -> mutation_executed
39
+ -> mutation_verified
40
+ -> done
41
+
42
+ stop states:
43
+ - stopped_overlap_needs_decision
44
+ - stopped_low_confidence
45
+ - stopped_explicit_reject
46
+ ```
47
+
48
+ Proposal artifact contract:
49
+ - human-readable Markdown proposal
50
+ - machine-readable JSON snapshot
51
+ - write temporary artifacts under `Proposal` (`tmp/new-idea-intake/<run-id>/proposal.md`) and `tmp/new-idea-intake/<run-id>/proposal.json`
52
+
53
+ If the Phase 1 preflight verdict is `pause_for_clarification`, stop and ask.
54
+ If the intake state machine stops at `stopped_overlap_needs_decision` or `stopped_low_confidence`, stop and ask.
55
+ If the intake state machine stops at `stopped_explicit_reject`, stop and record that the proposal was rejected; do not mutate GitHub.
56
+ After approval, start a separate async mutation pass (dispatched via the procedure) that consumes the approved proposal and emits a post-mutation verification artifact. Emit a concise post-mutation verification artifact and record what the mutation pass actually changed and verify the resulting issue/artifact state.
57
+
58
+ ## Unattended issue-first execution and automatic re-entry
59
+
60
+ When the user explicitly authorizes unattended execution for a specific issue/PR scope, continue through the normal loop mutations for that scope without stopping at every intermediate phase boundary.
61
+
62
+ Under that unattended execution contract:
63
+ - automatically detect the current lifecycle entrypoint from existing GitHub state
64
+ - use the deterministic helper/state-machine surface as the authority for current-state routing and next-step selection
65
+ - if local facts, GitHub facts, and helper/state-machine output do not agree, or the state is materially unclear, contradictory, off-trail, or not cleanly covered, stop and ask for human direction rather than guessing
66
+ - a pre-existing PR is not a stop-by-default condition
67
+ - If a PR already exists, classify the post-assignment seam before follow-up
68
+ - `waiting_for_initial_copilot_implementation`: keep waiting
69
+ - `linked_pr_ready_for_followup`: route to the existing PR follow-up path immediately; resume from that PR
70
+ - when routing leaves bootstrap wait for `linked_pr_ready_for_followup`, do not stop only because local isolation is required; re-enter the same PR follow-up from a safe isolated checkout/worktree
71
+ - When the draft PR appears, classify whether it is still the bootstrap-only Copilot draft before entering normal follow-up
72
+ - if a child async run exits while the deterministic state is still non-terminal (for example `waiting_for_copilot_review`), automatically resume/restart follow-up when continuation is feasible instead of requiring manual operator restart
73
+ - continue unattended until the human approval checkpoint unless a genuine stop condition is reached
74
+ - stop for a human approval decision by default
75
+ - after approval, report `waiting_for_merge_authorization` and stop again unless merge has been explicitly authorized
76
+ - this does **not** imply unattended merge by default
77
+
78
+ Issue-first shorthand such as `auto dev loop on issue <n>` should preserve this same stop boundary and human approval checkpoint default.
79
+
80
+ ## Phase 1 — Preflight intake
81
+
82
+ Before any automation, answer these questions:
83
+ 1. smallest executable work item
84
+ 2. existing issue check
85
+ 3. scope clarity
86
+ 4. acceptance criteria
87
+ 5. verification path
88
+ 6. active PR check
89
+
90
+ Accepted input types:
91
+ - GitHub issue number or URL
92
+ - plan-doc path
93
+ - abstract roadmap idea
94
+
95
+ Preflight verdicts:
96
+ - `proceed`
97
+ - `proceed_with_assumptions`
98
+ - `pause_for_clarification`
99
+
100
+ ## Phase 2 — Input normalization
101
+
102
+ ### From a GitHub issue number or URL
103
+
104
+ - if the input is a full GitHub issue URL, parse `<owner/name>` and `<number>`
105
+ - fetch with `gh issue view <number> --repo <owner/name> --json number,title,body,state,labels,assignees,milestone`
106
+ - If the issue is closed, stop for a user decision before proceeding
107
+ - detect an existing linked PR with the deterministic linked-PR helper:
108
+ `node <resolved-skill-scripts>/github/detect-linked-issue-pr.mjs --repo <resolved-repo> --issue <number>`
109
+ - treat the helper output as authoritative for linked-PR detection/selection
110
+ - do not re-implement linked-event query behavior, pagination, repo filtering, or tie-break logic
111
+ - do not rely only on PR title/body containing a literal issue number
112
+ - treat an open linked PR as the active implementation for this issue
113
+ - once an open linked PR exists, that PR is the only canonical follow-up artifact for the issue; attach follow-up work to it and do not open another PR unless the prior PR was explicitly superseded and reconciled first
114
+ - if a PR already exists, classify bootstrap-wait versus follow-up:
115
+ `node <resolved-skill-scripts>/loop/detect-initial-copilot-pr-state.mjs --repo <resolved-repo> --issue <number>`
116
+ - `waiting_for_initial_copilot_implementation`: keep waiting; in durable-auto mode use:
117
+ ```sh
118
+ node <resolved-skill-scripts>/loop/watch-initial-copilot-pr.mjs --repo <resolved-repo> --issue <number>
119
+ ```
120
+ - must use the dedicated `watch-initial-copilot-pr.mjs` watcher and its default 1-hour watch budget
121
+ - quiet/no-activity watch observations alone are non-terminal
122
+ - `ready_for_followup`: linked PR has become substantive; resume from that PR
123
+ - `timed_out`: observational first; refresh authoritative state
124
+ - if refreshed state is still `waiting_for_initial_copilot_implementation`, remain attached to the same durable wait seam and continue waiting
125
+ - if the refreshed state exits this seam, route based on that refreshed state instead of surfacing timeout attention
126
+ - when the refreshed state is `linked_pr_ready_for_followup`, re-enter normal PR follow-up; if the follow-up handoff carries `conductorRouting.handoffEnvelope.requiresLocalIsolation=true`, perform the expected isolated-checkout/worktree handoff and continue
127
+ - only surface timeout attention when the seam's durable watch budget is actually exhausted
128
+ - for explicit inspect/status requests, report the still-waiting state and exit normally
129
+ - carry that resolved repo slug through every later GitHub issue/PR command
130
+
131
+ ### From a plan-doc path
132
+
133
+ - Resolve the target repository slug for this work item before any GitHub search or mutation
134
+ - default to the current repository slug
135
+ - if the plan-doc reference explicitly points at another GitHub repository, resolve `<resolved-repo>` first
136
+ - search existing issues with:
137
+ ```sh
138
+ gh issue list --repo <resolved-repo> --state all --search "<title keywords>"
139
+ ```
140
+ - If a matching issue exists:
141
+ - if the matching issue is closed, stop for a user decision before proceeding
142
+ - if that matching issue turns out to be closed, stop for a user decision
143
+ - if a PR already exists, classify bootstrap-wait versus follow-up
144
+ - if a governing plan doc or roadmap section actually applies, follow the plan-doc normalization path above
145
+
146
+ ### From an abstract idea
147
+
148
+ - otherwise search existing issues directly
149
+ - if a matching issue exists, follow the issue-number/URL normalization path
150
+ - resolve `<resolved-repo>` for this work item using the same rule as the plan-doc path
151
+
152
+ ## Phase 3 — Async issue refinement
153
+
154
+ Before updating or assigning the issue, refine it asynchronously when practical. Keep issue refinement separate from the phase-scoped refiner used by the local implementation workflow. Use the `refiner` agent for this review-only issue-refinement chain, including the consolidation/fan-in step; do not route those comparison/synthesis steps through `dev-loop` + `local_implementation` (the strategy loaded by `skills/local-implementation`).
155
+
156
+ When issue refinement would benefit from structural/slop discovery and the likely code/doc surface is knowable, run the bounded audit first.
157
+ - write the issue-refinement audit artifact to `tmp/issues/issue-<number>/audit/refinement-audit-summary.json`
158
+ - use the same audit artifact shape as local phase refinement
159
+ - keep the audit bounded to the named files/areas for this issue; do not widen into a full-repo scan
160
+ - pass a concise audit summary into refiner fan-out and fan-in
161
+ - require the issue-refinement write-up to translate audit findings into scope, AC/DoD, risks, and explicit non-goals without silently broadening the issue
162
+
163
+ ## Phase 3b — Epic decomposition with GitHub sub-issue trees
164
+
165
+ When the work item is an umbrella/epic issue that must be decomposed into bounded child slices,
166
+ use **real GitHub sub-issue trees** as the default durable output — not body checklists, not
167
+ a manual follow-up linking step.
168
+
169
+ Prefer real sub-issue linkage over parent-body checklists when a work tree is intended.
170
+ A parent issue body should stay lean once the tree exists: keep scope, acceptance criteria, and
171
+ non-goals there, but do **not** duplicate the ordered child list in the body.
172
+
173
+ Full decomposition flow:
174
+
175
+ 1. refine umbrella issue framing (scope, acceptance criteria, non-goals)
176
+ 2. define bounded child slices — each slice must be independently closable
177
+ 3. create child issues with `gh issue create --repo <resolved-repo> --assignee @me`
178
+ 4. attach each child as a real sub-issue:
179
+ ```sh
180
+ node <resolved-skill-scripts>/github/manage-sub-issues.mjs add \
181
+ --repo <resolved-repo> --issue <parent-number> --child <child-number>
182
+ ```
183
+ 5. set execution order (highest priority first):
184
+ ```sh
185
+ node <resolved-skill-scripts>/github/manage-sub-issues.mjs reorder \
186
+ --repo <resolved-repo> --issue <parent-number> --order <n1,n2,...>
187
+ ```
188
+ 6. verify the resulting tree:
189
+ ```sh
190
+ node <resolved-skill-scripts>/github/manage-sub-issues.mjs verify \
191
+ --repo <resolved-repo> --issue <parent-number> --expected <n1,n2,...> [--ordered]
192
+ ```
193
+ 7. keep the parent issue body lean — sequencing and progress now live in the sub-issue tree
194
+
195
+ To inspect the current tree at any time:
196
+ ```sh
197
+ node <resolved-skill-scripts>/github/manage-sub-issues.mjs list \
198
+ --repo <resolved-repo> --issue <parent-number>
199
+ ```
200
+
201
+ Do **not** re-implement sub-issue management ad hoc or bypass `manage-sub-issues.mjs`.
202
+ Do **not** maintain a body checklist that duplicates the sub-issue tree.
203
+
204
+ For the full `manage-sub-issues.mjs` contract, use [Sub-Issue Tree Contract](../../docs/sub-issue-tree-contract.md) when working in the `dev-loops` source repository. That contract is a source-repo reference, not part of the bundled installed skill-doc surface. For installed or normalized skill copies, inspect the target repository docs/source directly instead of assuming a bundled shared-doc copy exists.
205
+
206
+ When an existing sub-issue tree needs **scope alignment, AC/DoD contracts, and delegation boundary refinement** across all levels (parent → children → grandchildren), use the [Epic Tree Refinement Procedure](./epic-tree-refinement-procedure.md) — it owns the deterministic depth-first, top-down-then-bottom-up refinement protocol.
207
+
208
+ ## Phase 4 — Copilot handoff and bootstrap wait
209
+
210
+ Before updating the GitHub issue body, show the diff and get explicit confirmation. Then use:
211
+ ```sh
212
+ gh issue edit <number> --repo <resolved-repo> --body-file <updated-body-file>
213
+ gh issue edit <number> --repo <resolved-repo> --add-assignee copilot-swe-agent
214
+ ```
215
+ Verify assignment with:
216
+ ```sh
217
+ gh issue view <number> --repo <resolved-repo> --json assignees
218
+ ```
219
+
220
+ When the linked PR becomes substantive, keep the shared loop scoped to the resolved repo, for example:
221
+ ```sh
222
+ node <resolved-skill-scripts>/loop/copilot-pr-handoff.mjs --repo <resolved-repo> --pr <number>
223
+ gh pr edit <pr-number> --repo <resolved-repo> --title "..." --body-file <body-file>
224
+ gh pr ready <pr-number> --repo <resolved-repo>
225
+ gh pr review <pr-number> --repo <resolved-repo> --approve --body "..."
226
+ node <resolved-skill-scripts>/github/detect-checkpoint-evidence.mjs --repo <resolved-repo> --pr <pr-number>
227
+ gh pr merge <pr-number> --repo <resolved-repo> --squash --delete-branch
228
+ ```
229
+
230
+ Bootstrap-wait interpretation remains fail-closed and observational-first:
231
+ - `ready_for_followup`: linked PR has become substantive; resume from that PR
232
+ - `timed_out`: observational first; refresh authoritative state
233
+ - if refreshed state is still `waiting_for_initial_copilot_implementation`, remain attached to the same durable wait seam and continue waiting
234
+ - if refreshed state exits that seam, route based on refreshed state instead of surfacing timeout attention
235
+
@@ -0,0 +1,72 @@
1
+ # Main-agent delegation contract
2
+
3
+ > **Absolute read-only boundary.** The main agent must never mutate files tracked by the repository.
4
+ > All mutations flow through the `dev-loop` async subagent.
5
+
6
+ ## Contract
7
+
8
+ The main agent is **read-only** for every file tracked by the repository. Every
9
+ write, edit, delete, commit, branch, push, and PR lifecycle operation must flow
10
+ through the `dev-loop` async subagent.
11
+
12
+ This contract is a hard rule, not a default or guideline. The main agent must
13
+ never rationalize a direct mutation — not because the work is small, not
14
+ because "the user said yes," not because it is running from a worktree.
15
+
16
+ ## Main agent owns (allowed)
17
+
18
+ - Read, inspect, search any repo file
19
+ - `git worktree list`, `git status`, `git log` (read-only git). `git fetch` is also allowed (updates local refs but does not touch tracked working-tree files).
20
+ - `gh issue view / create / edit / comment / close` (GitHub API, not file mutations)
21
+ - `gh pr view / list` (read-only GitHub API)
22
+ - Write to `/tmp` or other non-repo paths (e.g., issue body drafts)
23
+ - Delegate to the `dev-loop` agent (async, with worktree cwd)
24
+ - Report findings, ask questions, get confirmation
25
+ - `npm test`, `npm run verify` (read-only validation)
26
+
27
+ ## Main agent must NEVER
28
+
29
+ - `write`, `edit`, or delete any file tracked by the repo
30
+ - `git commit`, `git push`, create branches, create worktrees
31
+ - Run state-changing dev-loops CLI subcommands (`gate`, any state-changing `loop` subcommand, `pr` commands — those belong inside `dev-loop`).
32
+ - Delegate implementation to any agent other than `dev-loop`
33
+
34
+ ## Dev-loop agent (async) owns
35
+
36
+ - ALL file mutations in the repo (write, edit, delete)
37
+ - ALL git operations (branch, commit, push)
38
+ - ALL PR lifecycle (create, draft, review, merge)
39
+ - Sub-delegation to developer, fixer, review, quality agents
40
+
41
+ ## Boundary examples
42
+
43
+ | Operation | Verdict |
44
+ |---|---|
45
+ | `gh issue create --title "..." --body "..."` | Allowed — mutates GitHub, not files tracked by the repository |
46
+ | Write to `/tmp/issue-body.md` | Allowed — outside the repo |
47
+ | Write to `packages/core/src/foo.mjs` | **BREACH** — must delegate to `dev-loop` |
48
+ | `git status` | Allowed — read-only |
49
+ | `git commit -m "..."` | **BREACH** — must delegate to `dev-loop` |
50
+ | `subagent dev-loop` | Allowed — correct delegation |
51
+ | `subagent fixer` | Allowed only when called from within `dev-loop`; describe the task as part of the message |
52
+
53
+ ## Dev-loop startup
54
+
55
+ When a user triggers the dev loop, the main agent must immediately dispatch the
56
+ `dev-loop` async subagent. The subagent owns the startup resolver, route selection,
57
+ and all subsequent implementation steps. The main agent never runs `dev-loops loop startup`
58
+ directly.
59
+
60
+ ## Enforcement posture
61
+
62
+ - This contract is enforced by convention and review, not by tool-level guards.
63
+ - Mechanical enforcement (pre-commit hooks, tool-level write guards) is a
64
+ non-goal for this document and may be addressed in follow-up work.
65
+ - A `dev-loop` async subagent should reject delegation attempts that bypass
66
+ the contract (e.g., direct mutation requests from the main agent).
67
+
68
+ ## Non-goals
69
+
70
+ - Tool-level enforcement (file-write guards, pre-commit hooks)
71
+ - Changing dev-loop resolver behavior
72
+ - Modifying the subagent API itself
@@ -0,0 +1,29 @@
1
+ # Merge preconditions
2
+
3
+ Canonical owner for merge preconditions across all workflow families.
4
+
5
+ ## Required before merge
6
+
7
+ 1. ✅ CI green on current head (or crediblyGreen via `--local-validation-head-sha`)
8
+ 2. ✅ Draft gate satisfied (clean verdict)
9
+ 3. ✅ Pre-approval gate satisfied (clean verdict, current head)
10
+ 4. ✅ All review threads resolved
11
+ 5. ✅ Explicit merge authorization from operator
12
+ 6. ✅ PR body contains `Closes #N` or `Fixes #N`
13
+
14
+ ## Merge authorization
15
+
16
+ - Must be explicit for the active issue/PR scope
17
+ - `"Merge authorized if gates green"` is valid explicit authorization
18
+ - Implied approval from prior turns is not sufficient
19
+
20
+ ## Post-merge
21
+
22
+ - Remove merged worktree: `git worktree remove --force <path> && git worktree prune`
23
+ - Clean up stale branches
24
+
25
+ ## Cross-references
26
+
27
+ - [Confirmation rules](confirmation-rules.md)
28
+ - [Validation policy](validation-policy.md)
29
+ - [Stop conditions](stop-conditions.md)