claude-dev-env 1.92.1 → 1.93.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 (214) hide show
  1. package/CLAUDE.md +6 -2
  2. package/_shared/CLAUDE.md +2 -1
  3. package/_shared/advisor/CLAUDE.md +21 -0
  4. package/_shared/advisor/advisor-protocol.md +142 -0
  5. package/_shared/advisor/scripts/config/advisor_scripts_constants/__init__.py +1 -0
  6. package/_shared/advisor/scripts/config/advisor_scripts_constants/model_tier_run_validator_constants.py +86 -0
  7. package/_shared/advisor/scripts/model_tier_run_validator.py +246 -0
  8. package/_shared/advisor/scripts/pyproject.toml +3 -0
  9. package/_shared/advisor/scripts/tests/test_model_tier_run_validator.py +302 -0
  10. package/_shared/advisor/scripts/tests/test_tier_model_ids.py +180 -0
  11. package/_shared/advisor/scripts/tier_model_ids.py +164 -0
  12. package/_shared/pr-loop/CLAUDE.md +1 -0
  13. package/_shared/pr-loop/precatch-rubric.md +65 -0
  14. package/_shared/pr-loop/scripts/CLAUDE.md +1 -1
  15. package/_shared/pr-loop/scripts/code_rules_gate.py +137 -5
  16. package/_shared/pr-loop/scripts/post_audit_thread.py +1 -1
  17. package/_shared/pr-loop/scripts/pr_loop_shared_constants/CLAUDE.md +1 -1
  18. package/_shared/pr-loop/scripts/pr_loop_shared_constants/code_rules_gate_constants.py +16 -0
  19. package/_shared/pr-loop/scripts/pr_loop_shared_constants/reviews_disabled_constants.py +2 -1
  20. package/_shared/pr-loop/scripts/reviewer_availability.py +42 -12
  21. package/_shared/pr-loop/scripts/reviews_disabled.py +65 -21
  22. package/_shared/pr-loop/scripts/terminology_sweep.py +69 -21
  23. package/_shared/pr-loop/scripts/tests/CLAUDE.md +1 -1
  24. package/_shared/pr-loop/scripts/tests/fixtures/{copilot_internal_user_jonecho.json → copilot_internal_user_example.json} +1 -1
  25. package/_shared/pr-loop/scripts/tests/test_agent_config_carveout.py +1 -1
  26. package/_shared/pr-loop/scripts/tests/test_code_rules_gate.py +146 -2
  27. package/_shared/pr-loop/scripts/tests/test_copilot_quota.py +8 -8
  28. package/_shared/pr-loop/scripts/tests/test_reviewer_availability.py +18 -5
  29. package/_shared/pr-loop/scripts/tests/test_reviews_disabled.py +56 -5
  30. package/_shared/pr-loop/scripts/tests/test_terminology_sweep.py +104 -17
  31. package/agents/CLAUDE.md +3 -2
  32. package/agents/clasp-deployment-orchestrator.md +2 -2
  33. package/agents/code-advisor.md +7 -5
  34. package/agents/code-verifier.md +6 -2
  35. package/agents/session-advisor.md +27 -0
  36. package/audit-rubrics/category_rubrics/category-j-code-rules-compliance.md +1 -1
  37. package/audit-rubrics/category_rubrics/category-k-codebase-conflicts.md +1 -1
  38. package/audit-rubrics/prompts/category-a-api-contracts.md +2 -2
  39. package/audit-rubrics/prompts/category-b-selector-engine-compat.md +2 -2
  40. package/audit-rubrics/prompts/category-c-resource-cleanup.md +2 -2
  41. package/audit-rubrics/prompts/category-d-scoping-and-ordering.md +2 -2
  42. package/audit-rubrics/prompts/category-e-dead-code.md +2 -2
  43. package/audit-rubrics/prompts/category-f-silent-failures.md +2 -2
  44. package/audit-rubrics/prompts/category-g-bounds-and-overflow.md +2 -2
  45. package/audit-rubrics/prompts/category-h-security-boundaries.md +2 -2
  46. package/audit-rubrics/prompts/category-i-concurrency.md +2 -2
  47. package/audit-rubrics/prompts/category-j-code-rules-compliance.md +2 -2
  48. package/audit-rubrics/prompts/category-k-codebase-conflicts.md +2 -2
  49. package/audit-rubrics/prompts/category-l-behavior-equivalence.md +2 -2
  50. package/audit-rubrics/prompts/category-m-producer-consumer-cardinality.md +2 -2
  51. package/audit-rubrics/prompts/category-n-test-name-scenario-verifier.md +2 -2
  52. package/audit-rubrics/prompts/category-o-docstring-vs-impl-drift.md +2 -2
  53. package/audit-rubrics/prompts/category-p-name-vs-behavior-contract.md +2 -2
  54. package/bin/CLAUDE.md +1 -0
  55. package/bin/expand_home_directory_tokens.mjs +75 -0
  56. package/bin/install.mjs +21 -7
  57. package/bin/install.test.mjs +220 -10
  58. package/hooks/CLAUDE.md +1 -1
  59. package/hooks/blocking/CLAUDE.md +4 -1
  60. package/hooks/blocking/_path_setup.py +13 -0
  61. package/hooks/blocking/bash_pre_tool_use_dispatcher.py +281 -0
  62. package/hooks/blocking/code_rules_dead_module_constant.py +88 -16
  63. package/hooks/blocking/code_rules_enforcer.py +6 -0
  64. package/hooks/blocking/code_rules_imports_logging.py +34 -1
  65. package/hooks/blocking/code_rules_paths_syspath.py +1 -1
  66. package/hooks/blocking/code_rules_test_layout.py +272 -0
  67. package/hooks/blocking/nas_ssh_binary_enforcer.py +22 -12
  68. package/hooks/blocking/pii_prevention_blocker.py +781 -0
  69. package/hooks/blocking/pii_scanner.py +340 -0
  70. package/hooks/blocking/pre_tool_use_dispatcher.py +3 -3
  71. package/hooks/blocking/stop_dispatcher.py +84 -0
  72. package/hooks/blocking/test__path_setup.py +39 -0
  73. package/hooks/blocking/test_bash_dispatcher_interpreter_starts.py +61 -0
  74. package/hooks/blocking/test_bash_pre_tool_use_dispatcher.py +294 -0
  75. package/hooks/blocking/test_code_rules_enforcer_cross_skill_duplicate.py +1 -1
  76. package/hooks/blocking/test_code_rules_enforcer_dead_module_constant.py +51 -0
  77. package/hooks/blocking/test_code_rules_enforcer_dead_module_constant_read_cap.py +103 -0
  78. package/hooks/blocking/test_code_rules_enforcer_dot_test_pattern.py +1 -1
  79. package/hooks/blocking/test_code_rules_enforcer_file_global_constants.py +1 -1
  80. package/hooks/blocking/test_code_rules_enforcer_hardcoded_user_path.py +11 -11
  81. package/hooks/blocking/test_code_rules_enforcer_naive_datetime.py +1 -1
  82. package/hooks/blocking/test_code_rules_enforcer_same_file_inline_duplicate.py +1 -1
  83. package/hooks/blocking/test_code_rules_enforcer_test_layout.py +111 -0
  84. package/hooks/blocking/test_code_rules_enforcer_type_checking_scope.py +76 -0
  85. package/hooks/blocking/test_destructive_command_blocker.py +29 -9
  86. package/hooks/blocking/test_gh_body_arg_blocker.py +3 -3
  87. package/hooks/blocking/test_nas_ssh_binary_enforcer.py +96 -39
  88. package/hooks/blocking/test_pii_prevention_blocker.py +905 -0
  89. package/hooks/blocking/test_pii_prevention_windows_git_path.py +41 -0
  90. package/hooks/blocking/test_pii_scanner.py +165 -0
  91. package/hooks/blocking/test_pr_description_enforcer_pr_number.py +1 -1
  92. package/hooks/blocking/test_pre_tool_use_dispatcher.py +14 -13
  93. package/hooks/blocking/test_stop_dispatcher.py +187 -0
  94. package/hooks/blocking/test_verdict_directory_write_blocker.py +1 -1
  95. package/hooks/blocking/test_volatile_path_in_post_blocker.py +3 -3
  96. package/hooks/blocking/volatile_path_in_post_blocker.py +54 -5
  97. package/hooks/diagnostic/migrations/README.md +25 -26
  98. package/hooks/diagnostic/test_hook_log_extractor.py +10 -10
  99. package/hooks/hooks.json +10 -120
  100. package/hooks/hooks_constants/CLAUDE.md +12 -3
  101. package/hooks/hooks_constants/bash_pre_tool_use_dispatcher_constants.py +78 -0
  102. package/hooks/hooks_constants/dead_module_constant_constants.py +1 -0
  103. package/hooks/hooks_constants/hosted_hook_runner.py +73 -0
  104. package/hooks/hooks_constants/local_identity.py +182 -0
  105. package/hooks/hooks_constants/nas_ssh_binary_enforcer_constants.py +4 -37
  106. package/hooks/hooks_constants/pii_prevention_constants.py +299 -0
  107. package/hooks/hooks_constants/pre_tool_use_dispatcher_constants.py +4 -0
  108. package/hooks/hooks_constants/python_style_checks_constants.py +15 -0
  109. package/hooks/hooks_constants/stop_dispatcher_constants.py +26 -0
  110. package/hooks/hooks_constants/test_bash_pre_tool_use_dispatcher_constants.py +87 -0
  111. package/hooks/hooks_constants/test_hardcoded_user_path_constants.py +2 -2
  112. package/hooks/hooks_constants/test_hosted_hook_runner.py +101 -0
  113. package/hooks/hooks_constants/test_layout_constants.py +28 -0
  114. package/hooks/hooks_constants/test_local_identity.py +88 -0
  115. package/hooks/hooks_constants/test_session_env_cleanup_constants.py +1 -1
  116. package/hooks/hooks_constants/test_stop_dispatcher_constants.py +32 -0
  117. package/hooks/validators/README.md +5 -6
  118. package/hooks/validators/__init__.py +2 -2
  119. package/hooks/validators/python_style_checks.py +298 -243
  120. package/hooks/validators/run_all_validators.py +6 -0
  121. package/hooks/validators/test_python_style_checks.py +278 -163
  122. package/package.json +2 -2
  123. package/rules/CLAUDE.md +2 -1
  124. package/rules/bdd.md +1 -1
  125. package/rules/nas-ssh-invocation.md +6 -4
  126. package/rules/no-justification-noise.md +61 -0
  127. package/scripts/test_setup_project_paths.py +1 -1
  128. package/skills/CLAUDE.md +6 -3
  129. package/skills/_shared/pr-loop/scripts/_path_resolver.py +2 -2
  130. package/skills/_shared/pr-loop/scripts/build_audit_prompt.py +1 -1
  131. package/skills/_shared/pr-loop/scripts/build_fix_prompt.py +1 -1
  132. package/skills/_shared/pr-loop/scripts/test__path_resolver.py +42 -3
  133. package/skills/_shared/pr-loop/scripts/test_build_audit_prompt.py +11 -11
  134. package/skills/_shared/pr-loop/scripts/test_build_fix_prompt.py +26 -3
  135. package/skills/_shared/pr-loop/scripts/test_preflight_worktree.py +49 -25
  136. package/skills/autoconverge/CLAUDE.md +3 -3
  137. package/skills/autoconverge/SKILL.md +113 -35
  138. package/skills/autoconverge/reference/CLAUDE.md +2 -2
  139. package/skills/autoconverge/reference/convergence.md +44 -22
  140. package/skills/autoconverge/reference/gotchas.md +11 -0
  141. package/skills/autoconverge/reference/stop-conditions.md +23 -13
  142. package/skills/autoconverge/workflow/CLAUDE.md +2 -1
  143. package/skills/autoconverge/workflow/converge.clean-audit.test.mjs +15 -19
  144. package/skills/autoconverge/workflow/converge.contract.test.mjs +43 -42
  145. package/skills/autoconverge/workflow/converge.copilot-gate.test.mjs +141 -16
  146. package/skills/autoconverge/workflow/converge.fix-recovery.test.mjs +2 -2
  147. package/skills/autoconverge/workflow/converge.mjs +329 -68
  148. package/skills/autoconverge/workflow/converge.path-aware.test.mjs +1 -1
  149. package/skills/autoconverge/workflow/converge.precatch.test.mjs +152 -0
  150. package/skills/autoconverge/workflow/converge.run-input.test.mjs +3 -3
  151. package/skills/autoconverge/workflow/converge_multi.run-input.test.mjs +15 -15
  152. package/skills/autoconverge/workflow/test_convergence_summary.py +6 -6
  153. package/skills/bdd-protocol/SKILL.md +4 -5
  154. package/skills/bdd-protocol/references/anti-patterns.md +1 -1
  155. package/skills/bugteam/SKILL.md +8 -0
  156. package/skills/bugteam/reference/copilot-gap-analysis.md +20 -20
  157. package/skills/bugteam/reference/obstacles/audit-walk-categories.md +1 -1
  158. package/skills/bugteam/reference/team-setup.md +7 -5
  159. package/skills/bugteam/scripts/reflow_skill_md.py +1 -1
  160. package/skills/copilot-finding-triage/SKILL.md +124 -0
  161. package/skills/copilot-finding-triage/reference/tier-rubric.md +49 -0
  162. package/skills/copilot-finding-triage/scripts/conftest.py +8 -0
  163. package/skills/copilot-finding-triage/scripts/copilot_finding_triage_constants/__init__.py +0 -0
  164. package/skills/copilot-finding-triage/scripts/copilot_finding_triage_constants/config/__init__.py +0 -0
  165. package/skills/copilot-finding-triage/scripts/copilot_finding_triage_constants/config/notify_ntfy_constants.py +32 -0
  166. package/skills/copilot-finding-triage/scripts/notify_ntfy.py +192 -0
  167. package/skills/copilot-finding-triage/scripts/test_notify_ntfy.py +141 -0
  168. package/skills/copilot-finding-triage/templates/notification.md +34 -0
  169. package/skills/copilot-review/SKILL.md +8 -6
  170. package/skills/findbugs/SKILL.md +4 -0
  171. package/skills/fixbugs/SKILL.md +8 -7
  172. package/skills/gotcha/CLAUDE.md +2 -2
  173. package/skills/gotcha/SKILL.md +4 -4
  174. package/skills/log-audit/SKILL.md +4 -6
  175. package/skills/monitor-open-prs/CLAUDE.md +1 -1
  176. package/skills/monitor-open-prs/SKILL.md +6 -1
  177. package/skills/orchestrator/SKILL.md +74 -78
  178. package/skills/orchestrator-refresh/SKILL.md +24 -12
  179. package/skills/post-audit-findings/SKILL.md +5 -9
  180. package/skills/pr-consistency-audit/SKILL.md +5 -1
  181. package/skills/pr-converge/CLAUDE.md +1 -1
  182. package/skills/pr-converge/SKILL.md +86 -47
  183. package/skills/pr-converge/reference/CLAUDE.md +1 -1
  184. package/skills/pr-converge/reference/convergence-gates.md +20 -17
  185. package/skills/pr-converge/reference/examples.md +63 -47
  186. package/skills/pr-converge/reference/fix-protocol.md +15 -15
  187. package/skills/pr-converge/reference/ground-rules.md +11 -7
  188. package/skills/pr-converge/reference/multi-pr-orchestration.md +6 -5
  189. package/skills/pr-converge/reference/per-tick.md +129 -107
  190. package/skills/pr-converge/reference/state-schema.md +15 -10
  191. package/skills/pr-converge/scripts/check_convergence.py +5 -4
  192. package/skills/pr-converge/scripts/test_check_convergence.py +6 -4
  193. package/skills/pr-fix-protocol/SKILL.md +3 -8
  194. package/skills/pr-loop-cloud-transport/SKILL.md +102 -0
  195. package/skills/pr-loop-cloud-transport/reference/identity-and-hooks.md +40 -0
  196. package/skills/pr-loop-cloud-transport/reference/substitution-matrix.md +48 -0
  197. package/skills/pr-loop-lifecycle/SKILL.md +5 -9
  198. package/skills/pr-scope-resolve/SKILL.md +3 -6
  199. package/skills/privacy-hygiene/SKILL.md +114 -0
  200. package/skills/qbug/SKILL.md +8 -8
  201. package/skills/rebase/SKILL.md +5 -1
  202. package/skills/refine/SKILL.md +4 -5
  203. package/skills/reviewer-gates/SKILL.md +7 -11
  204. package/skills/session-log/SKILL.md +4 -1
  205. package/skills/skill-builder/SKILL.md +3 -6
  206. package/skills/structure-prompt/SKILL.md +4 -5
  207. package/skills/team-advisor/SKILL.md +56 -0
  208. package/skills/test_markdown_link_integrity.py +10 -6
  209. package/skills/update/SKILL.md +5 -1
  210. package/skills/usage-pause/SKILL.md +14 -5
  211. package/skills/usage-pause/scripts/resolve_usage_window.py +83 -5
  212. package/skills/usage-pause/scripts/test_resolve_usage_window.py +185 -17
  213. package/skills/usage-pause/scripts/usage_pause_constants/resolve_usage_window_constants.py +4 -3
  214. package/skills/verified-build/SKILL.md +4 -9
@@ -1,20 +1,26 @@
1
1
  ---
2
2
  name: pr-converge
3
3
  description: >-
4
- Drives the current PR to convergence by looping Cursor Bugbot, a
5
- code-review pass, a second-opinion bug audit, and Copilot applying
6
- TDD fixes, posting inline replies, and re-triggering reviewers each
7
- tick until all reviewers are clean on the same HEAD. Use when the user
8
- says
9
- '/pr-converge', 'drive PR to convergence', 'loop bugbot and bugteam',
10
- 'babysit bugbot and bugteam', 'until both are clean', or 'converge this
11
- PR'.
4
+ Loops Cursor Bugbot, a code review, a bug audit, and Copilot on the current
5
+ PR, applying TDD fixes until all are clean on one HEAD. Use when the user says
6
+ '/pr-converge', 'drive PR to convergence', 'loop bugbot and bugteam', 'babysit
7
+ bugbot and bugteam', 'until both are clean', or 'converge this PR'.
12
8
  ---
13
9
 
14
10
  # PR Converge
15
11
 
16
- One tick per invocation. Bugbot code-review ↔ bugteam ↔ Copilot loop on
17
- a draft PR until all are clean on the same `HEAD` and mergeable.
12
+ One tick per invocation. A code-review ↔ bugteam ↔ Bugbot ↔ Copilot loop on
13
+ a draft PR: the internal code-review and bugteam passes drive the code to clean
14
+ first, then Cursor Bugbot and Copilot run as terminal confirmation gates, until
15
+ all are clean on the same `HEAD` and mergeable.
16
+
17
+ ## Transport check (before any GitHub step)
18
+
19
+ Run `command -v gh`; when it succeeds, run `gh auth status`; once the PR
20
+ scope is resolved, run `gh api repos/<owner>/<repo> --jq .permissions.push`
21
+ and take `true` as the pass. When any check fails, run the
22
+ `pr-loop-cloud-transport` skill first and route every `gh` operation in this
23
+ skill through its substitution matrix.
18
24
 
19
25
  ## Pre-flight
20
26
 
@@ -50,7 +56,7 @@ Before Step 0, check
50
56
  `$CLAUDE_JOB_DIR/pr-converge-state.json` is absent but that handoff exists, seed
51
57
  `phase`, `tick_count`, and the clean-at SHAs from the run's `state-copy.json`, so
52
58
  a fresh session continues where the last one stopped rather than restarting at
53
- BUGBOT.
59
+ CODE_REVIEW.
54
60
 
55
61
  ## Copilot quota pre-check (start of run)
56
62
 
@@ -64,6 +70,29 @@ no request, no poll, no agent — and exports
64
70
  pending-requested-reviews gate and the run still marks ready on the remaining
65
71
  signals.
66
72
 
73
+ ## Copilot findings — two-tier triage
74
+
75
+ The Copilot step tiers each finding it surfaces. A **self-healing** finding is
76
+ pure style, type hints, misplaced or unused imports, formatting, magic-value
77
+ extraction, a test-only change, a doc-or-description vs code mismatch, or code
78
+ de-duplication — a fix that cannot change observable runtime behavior for
79
+ production callers. Self-healing findings flow into the existing fix tick and
80
+ count toward convergence, with no user alert. The tick-paced loop holds them
81
+ naturally: the fix lands on `current_head`, the next tick re-checks, and the run
82
+ converges when the Copilot step is clean.
83
+
84
+ A **code-concern** finding is behavior-changing or needs a product decision:
85
+ logic or correctness, security, data handling, error-handling semantics, or
86
+ concurrency. Tier a finding as code-concern whenever the tier is in doubt. On
87
+ one or more code-concern findings, do not auto-fix them and do not let the tick
88
+ mark the PR ready. Run the
89
+ [`copilot-finding-triage`](../copilot-finding-triage/SKILL.md) gate: send the
90
+ ntfy alert with the finding summary and the Copilot review link, then hold for
91
+ the user's response on a 45-minute deadline that spans ticks — carry the
92
+ deadline in the run's persisted state so each tick reads it on entry. Act on the
93
+ user's direction when it arrives inside the window; when the deadline passes
94
+ with no response, run teardown and report the code-concern findings un-reviewed.
95
+
67
96
  ## Budget-aware tick boundaries
68
97
 
69
98
  Before starting any tick, estimate whether the remaining session/usage
@@ -137,7 +166,7 @@ the `persistent_agents` map
137
166
  within one bounded wait, drop the map entry, spawn a fresh named agent,
138
167
  record it, and continue the tick. Never abort a tick on a stale id;
139
168
  never retry the same dead id.
140
- - **Fresh every round (never persisted):** the Step 5 `/code-review --fix`
169
+ - **Fresh every round (never persisted):** the Step 5 `/code-review high --fix`
141
170
  pass and the Step 6 bugteam audit (unbiased eyes each round; the
142
171
  enforcer needs the formal Skill call), and every `code-verifier` — a
143
172
  named code-verifier never fires `SubagentStop`, so no verdict mints (see
@@ -188,7 +217,7 @@ post a fresh PR in a fresh branch based on origin main to the user.
188
217
  Windows is Git Bash which cannot execute PowerShell cmdlets. Route all
189
218
  PowerShell work through the PowerShell tool or `pwsh -NoProfile -File`.
190
219
  - **Cross-repo PR: route cwd into the PR worktree before `/code-review`** —
191
- `/code-review --fix` (Step 5) audits the repo of the current working
220
+ `/code-review high --fix` (Step 5) audits the repo of the current working
192
221
  directory. When the session is rooted in a different repo than the PR,
193
222
  `EnterWorktree` cannot re-root (it is scoped to the session's repo);
194
223
  resolve the PR worktree and `cd` into it per
@@ -237,7 +266,7 @@ round as converged. This rule holds every tick, every loop, every PR.
237
266
  and [§ Step 1.5](reference/per-tick.md)
238
267
 
239
268
  - [ ] **Step 2: Initialize loop state**
240
- `phase = BUGBOT`; all counters at zero; `run_name` resolved.
269
+ `phase = CODE_REVIEW`; all counters at zero; `run_name` resolved.
241
270
 
242
271
  - [ ] **Step 3: Mergeability check**
243
272
  See: [`reference/convergence-gates.md` § (c)](reference/convergence-gates.md)
@@ -249,37 +278,38 @@ round as converged. This rule holds every tick, every loop, every PR.
249
278
  - [ ] mergeable → advance to Step 4
250
279
  - [ ] not mergeable → rebase → force-push → return to Step 1
251
280
 
252
- - [ ] **Step 4: BUGBOT — fetch, decide, fix, reply, resolve**
253
- See: [`reference/per-tick.md` § Step 2 BUGBOT + Step 3](reference/per-tick.md)
281
+ - [ ] **Step 4: BUGBOT — terminal Bugbot confirmation gate**
282
+ The terminal external gate. Step 6 routes here after BUGTEAM converges, so
283
+ Bugbot confirms code the internal passes already drove to clean.
284
+ See: [`reference/per-tick.md` § BUGBOT terminal gate + Step 3](reference/per-tick.md)
254
285
 
255
- - [ ] **Opt-out gate (runs first, every BUGBOT entry).**
286
+ - [ ] **Availability gate (runs first, every BUGBOT entry).**
256
287
  Gate semantics live in the `reviewer-gates` skill
257
- (`../reviewer-gates/SKILL.md` § Gate 1).
288
+ (`../reviewer-gates/SKILL.md` § Gate 1). Cursor Bugbot is off by default and runs only when `CLAUDE_REVIEWS_ENABLED` lists `bugbot`; a `bugbot` token in `CLAUDE_REVIEWS_DISABLED` keeps it off even then.
258
289
  `python "$HOME/.claude/_shared/pr-loop/scripts/reviews_disabled.py" --reviewer bugbot`
259
- - [ ] Exit 0 (`CLAUDE_REVIEWS_DISABLED` lists `bugbot`) → set `bugbot_down = true`, `phase = CODE_REVIEW`, advance to Step 5 (bypass). Cursor Bugbot is skipped for the entire run.
290
+ - [ ] Exit 0 (Bugbot disabled for this run — the default) → set `bugbot_down = true`, advance to the Step 7 convergence gates (no trigger, no wait, no agent). Cursor Bugbot is skipped for the entire run.
260
291
  - [ ] Exit 1 → continue below.
261
292
 
262
293
  Fetch bugbot reviews + inline comments on `current_head`.
263
294
 
264
295
  - [ ] **dirty** (findings on `current_head`) →
265
296
  - [ ] Apply the `pr-fix-protocol` skill (`../pr-fix-protocol/SKILL.md`) to this tick's findings
266
- - [ ] Push → return to Step 4
297
+ - [ ] Push → reset `bugbot_clean_at = null`, `code_review_clean_at = null` → `phase = CODE_REVIEW` → return to Step 5
267
298
  - [ ] **clean** (no findings on `current_head`) →
268
299
  - [ ] Count ALL unresolved threads on PR (`is_resolved == false`) → zero? advance; >0? fix + resolve first
269
300
  - [ ] `bugbot_clean_at = current_head`
270
- - [ ] `phase = CODE_REVIEW`
271
- - [ ] Advance to Step 5
301
+ - [ ] Advance to the Step 7 convergence gates
272
302
  - [ ] **no review yet / commit_id mismatch** →
273
303
  Apply the `reviewer-gates` skill's Bugbot flow
274
304
  (`../reviewer-gates/SKILL.md` § Gate 3) against `current_head`,
275
305
  then map its outcomes:
276
- - [ ] Silent pass → `bugbot_clean_at = current_head` → `phase = CODE_REVIEW` advance to Step 5
306
+ - [ ] Silent pass → `bugbot_clean_at = current_head` → advance to the Step 7 convergence gates
277
307
  - [ ] Already queued, or trigger acknowledged → schedule 360s wakeup → return to Step 4 next tick
278
- - [ ] Bugbot down → `bugbot_down = true` → `phase = CODE_REVIEW` advance to Step 5 (bypass)
279
- - [ ] **Step 5: CODE-REVIEW — run, fix, reset, advance**
280
- See: [`reference/per-tick.md` § Step 2 CODE_REVIEW](reference/per-tick.md)
281
-
282
- Pre-condition: `bugbot_clean_at == current_head` (or `bugbot_down == true`).
308
+ - [ ] Bugbot down → `bugbot_down = true` → advance to the Step 7 convergence gates (bypass)
309
+ - [ ] **Step 5: CODE-REVIEW — entry phase: static sweep, review, fix, advance**
310
+ The first internal step of every convergence tick (Step 2 seeds
311
+ `phase = CODE_REVIEW`), re-entered after any fix push.
312
+ See: [`reference/per-tick.md` § CODE_REVIEW entry](reference/per-tick.md)
283
313
 
284
314
  Pre-condition: the working directory is the Step 1.5 PR worktree on
285
315
  `current_head` (`git rev-parse --show-toplevel` is that checkout).
@@ -288,18 +318,28 @@ round as converged. This rule holds every tick, every loop, every PR.
288
318
  current working directory, so this routing targets the real PR
289
319
  diff. This `cd` is routine and automatic.
290
320
 
291
- Run Claude Code's built-in `/code-review --fix` on the full
321
+ - [ ] **Static sweep — runs first, before `/code-review`.** Run the
322
+ deterministic gates over the full `origin/main...HEAD` changed files:
323
+ `python "$HOME/.claude/_shared/pr-loop/scripts/code_rules_gate.py" --base origin/main`,
324
+ `ruff`, `mypy`, and stem-matched `pytest`.
325
+ - [ ] Any failure → apply the `pr-fix-protocol` skill
326
+ (`../pr-fix-protocol/SKILL.md`), commit/push, reset
327
+ `bugbot_clean_at = null` and `code_review_clean_at = null`, stay
328
+ `phase = CODE_REVIEW`, and re-run (return to Step 5).
329
+ - [ ] Clean → run `/code-review` below.
330
+
331
+ Run Claude Code's built-in `/code-review high --fix` on the full
292
332
  `origin/main...HEAD` diff —
293
333
  the [local diff review](https://code.claude.com/docs/en/code-review#review-a-diff-locally)
294
334
  — so it reviews the diff and applies its findings to the working
295
- tree. Pass no effort argument, so the review uses the session's
296
- current effort.
335
+ tree. Invoke `/code-review high --fix` so the pre-catch pass gets broad
336
+ coverage regardless of the session's current effort.
297
337
 
298
338
  **Scope: the FULL `origin/main...HEAD` diff every tick** — every file
299
339
  the PR touches. Do not delta-scope to commits added since the prior
300
340
  clean SHA, do not scope to a single file, do not scope to bugbot's
301
341
  flagged paths. Before running, confirm the working tree is on the
302
- PR's HEAD with no uncommitted edits, then invoke `/code-review --fix`
342
+ PR's HEAD with no uncommitted edits, then invoke `/code-review high --fix`
303
343
  with no path arguments so it audits the whole branch diff against
304
344
  `origin/main`. A partial-scope round does not count and cannot set
305
345
  `code_review_clean_at`.
@@ -307,8 +347,7 @@ round as converged. This rule holds every tick, every loop, every PR.
307
347
  - [ ] **fixes applied** (working tree changed) →
308
348
  - [ ] Commit the applied fixes (one commit) → push
309
349
  - [ ] reset `bugbot_clean_at = null`, `code_review_clean_at = null`
310
- - [ ] Re-trigger bugbot (Step 4 "no review yet" checklist)
311
- - [ ] `phase = BUGBOT` → schedule 360s wakeup → return to Step 4
350
+ - [ ] stay `phase = CODE_REVIEW` return to Step 5 (internal-first)
312
351
  - [ ] **clean** (no changes applied) →
313
352
  - [ ] Zero unresolved threads per the `pr-fix-protocol` sweep (`../pr-fix-protocol/SKILL.md`) → advance; else fix + resolve first (same skill)
314
353
  - [ ] `code_review_clean_at = current_head`
@@ -338,21 +377,21 @@ round as converged. This rule holds every tick, every loop, every PR.
338
377
 
339
378
  - [ ] **bugteam pushed new commits** →
340
379
  - [ ] Verify all bugteam review threads replied + resolved
341
- - [ ] Re-trigger bugbot (Step 4 "no review yet" checklist)
342
- - [ ] `phase = BUGBOT` → schedule 360s wakeup → return to Step 4
343
- - [ ] **converged (zero findings) + `bugbot_clean_at == current_head`**
380
+ - [ ] reset `bugbot_clean_at = null`, `code_review_clean_at = null`
381
+ - [ ] `phase = CODE_REVIEW` → schedule 360s wakeup → return to Step 5
382
+ - [ ] **converged (zero findings), no push**
344
383
  - [ ] Count ALL unresolved threads on PR (`is_resolved == false`) → zero? advance; >0? fix + resolve first
345
- - [ ] Advance to Step 7
346
- - [ ] **converged + `bugbot_clean_at ≠ current_head`** →
347
- `phase = BUGBOT` → schedule 360s wakeup → return to Step 4
384
+ - [ ] `phase = BUGBOT` → advance to Step 4 (terminal Bugbot gate)
348
385
  - [ ] **findings without committed fixes** →
349
386
  - [ ] Apply the `pr-fix-protocol` skill (`../pr-fix-protocol/SKILL.md`) to the findings
350
- - [ ] Push → `phase = BUGBOT` → return to Step 4
387
+ - [ ] Push → reset `bugbot_clean_at = null`, `code_review_clean_at = null` → `phase = CODE_REVIEW` → return to Step 5
351
388
 
352
389
  - [ ] **Step 7: Convergence gates**
353
390
  See: [`reference/convergence-gates.md`](reference/convergence-gates.md)
354
391
 
355
- Pre-condition: Step 6 converged AND `bugbot_clean_at == current_head`.
392
+ Pre-condition: Step 6 converged AND (`bugbot_clean_at == current_head` OR
393
+ `bugbot_down`). The terminal Bugbot gate (Step 4) sets that state just
394
+ before these gates run.
356
395
  Count unresolved threads before each gate.
357
396
 
358
397
  **(a) Universal unresolved-thread sweep**
@@ -361,13 +400,13 @@ round as converged. This rule holds every tick, every loop, every PR.
361
400
  pull_request_read(method="get_review_comments")
362
401
  → filter threads where is_resolved == false
363
402
  ```
364
- - [ ] Any unresolved? → apply the `pr-fix-protocol` skill's unresolved-thread sweep (`../pr-fix-protocol/SKILL.md`). Push if any code changed → return to Step 4
403
+ - [ ] Any unresolved? → apply the `pr-fix-protocol` skill's unresolved-thread sweep (`../pr-fix-protocol/SKILL.md`). Push if any code changed → reset markers → `phase = CODE_REVIEW` → return to Step 5
365
404
  - [ ] When `copilot_down == true` (start-of-run quota pre-check), skip the Copilot fetch below — no request, no poll, no agent — and continue to gate (b); the Copilot gate is bypassed for the whole run.
366
405
  - [ ] Fetch Copilot review on `current_head` (top-level review state — uses get_reviews, identifies by reviewer):
367
406
  ```
368
407
  python ~/.claude/skills/pr-converge/scripts/fetch_copilot_reviews.py --owner <O> --repo <R> --pr-number <N>
369
408
  ```
370
- - [ ] dirty → apply the `pr-fix-protocol` skill (`../pr-fix-protocol/SKILL.md`) → push → return to Step 4
409
+ - [ ] dirty → apply the `pr-fix-protocol` skill (`../pr-fix-protocol/SKILL.md`) → push → reset markers → `phase = CODE_REVIEW` → return to Step 5
371
410
  - [ ] clean (no findings) → `copilot_clean_at = current_head` → gate (b)
372
411
  - [ ] no review yet → gate (b)
373
412
 
@@ -399,7 +438,7 @@ round as converged. This rule holds every tick, every loop, every PR.
399
438
  → count threads where is_resolved == false
400
439
  ```
401
440
  - [ ] zero unresolved → gate (e)
402
- - [ ] unresolved → apply the `pr-fix-protocol` skill's unresolved-thread sweep (`../pr-fix-protocol/SKILL.md`). Push if code changed → return to Step 4
441
+ - [ ] unresolved → apply the `pr-fix-protocol` skill's unresolved-thread sweep (`../pr-fix-protocol/SKILL.md`). Push if code changed → reset markers → `phase = CODE_REVIEW` → return to Step 5
403
442
 
404
443
  **(e) Mark ready**
405
444
  - [ ] When `copilot_down == true`, export `CLAUDE_REVIEWS_DISABLED="copilot"` in this tick's shell before the check below, so it bypasses the Copilot review gate and the pending-requested-reviews gate.
@@ -409,7 +448,7 @@ round as converged. This rule holds every tick, every loop, every PR.
409
448
  --owner <O> --repo <R> --pr-number <N>
410
449
  ```
411
450
  - [ ] Exit 0 (all pass) → `update_pull_request(draft=false)` → advance to Step 8
412
- - [ ] Exit 1 (FAIL lines) → address each failure → return to Step 4
451
+ - [ ] Exit 1 (FAIL lines) → address each failure → reset markers → `phase = CODE_REVIEW` → return to Step 5
413
452
  - [ ] Exit 2 (gh error) → retry once; persistent → stop
414
453
 
415
454
  - [ ] **Step 7a: COPILOT_WAIT — fetch Copilot, decide**
@@ -424,7 +463,7 @@ round as converged. This rule holds every tick, every loop, every PR.
424
463
  `copilot_clean_at = current_head` → return to Step 7 (re-validate gates b, d, e)
425
464
  - [ ] **dirty (findings present)** →
426
465
  - [ ] Apply the `pr-fix-protocol` skill (`../pr-fix-protocol/SKILL.md`) to the findings
427
- - [ ] Push → `phase = BUGBOT` → return to Step 4
466
+ - [ ] Push → reset markers → `phase = CODE_REVIEW` → return to Step 5
428
467
  - [ ] **no review yet** →
429
468
  increment `copilot_wait_count` → ≥ 3 = hard blocker → stop
430
469
  schedule 360s wakeup → return to Step 7a next tick
@@ -6,7 +6,7 @@ Reference documents for the `pr-converge` skill. These files define the per-tick
6
6
 
7
7
  | File | Purpose |
8
8
  |---|---|
9
- | `per-tick.md` | Step-by-step procedure for one tick (resolve HEAD, run BUGBOT, CODE_REVIEW, BUGTEAM, COPILOT_WAIT phases, schedule next wakeup) |
9
+ | `per-tick.md` | Step-by-step procedure for one tick (resolve HEAD, run the internal CODE_REVIEW and BUGTEAM phases, then the terminal BUGBOT and COPILOT_WAIT gates, schedule next wakeup) |
10
10
  | `convergence-gates.md` | Six gates that must all pass before the PR is marked ready for review |
11
11
  | `fix-protocol.md` | pr-converge deltas on the `pr-fix-protocol` skill: multi-PR teammate obligations and the same-tick bugbot re-trigger rule |
12
12
  | `ground-rules.md` | Non-negotiable constraints for the convergence loop |
@@ -1,9 +1,10 @@
1
1
  # Convergence gates
2
2
 
3
- Run **only** when Step 2 BUGTEAM reports `convergence (zero findings)` AND
4
- `bugbot_clean_at == current_head` AND no push during bugteam tick. Gates run
5
- in order; first failure determines next-tick behavior. Mark PR ready only
6
- when all six pass.
3
+ Run **only** after the terminal Bugbot gate confirms the HEAD
4
+ (`bugbot_clean_at == current_head` OR `bugbot_down`), which runs just before
5
+ these gates once Step 2 BUGTEAM reports `convergence (zero findings)` with no
6
+ push during the bugteam tick. Gates run in order; first failure determines
7
+ next-tick behavior. Mark PR ready only when all six pass.
7
8
 
8
9
  **Mandatory evidence rule:** Every gate that fetches data MUST produce a
9
10
  summary of its findings before proceeding to the next gate. Gate (f) MUST
@@ -36,19 +37,20 @@ Decide (four branches; match first whose predicate holds):
36
37
  - **`classification == "dirty"` with non-empty inline comments matching
37
38
  `pull_request_review_id`:** Fix protocol input (same shape as bugbot
38
39
  dirty). Apply the `pr-fix-protocol` skill
39
- (`../../pr-fix-protocol/SKILL.md`) Step 3 in same tick.
40
- Reset `bugbot_clean_at = null` AND `copilot_clean_at = null`, `phase =
41
- BUGBOT`, schedule next wakeup, return. Full back-to-back-clean cycle
42
- plus all six gates must hold again on new HEAD.
40
+ (`../../pr-fix-protocol/SKILL.md`) in the same tick.
41
+ Reset `bugbot_clean_at = null`, `code_review_clean_at = null`, AND
42
+ `copilot_clean_at = null`, `phase = CODE_REVIEW`, schedule next wakeup,
43
+ return. Full back-to-back-clean cycle plus all six gates must hold again on
44
+ new HEAD.
43
45
  - **`classification == "dirty"` with empty inline comments matching
44
46
  `pull_request_review_id`:** Copilot posted findings only in review body
45
47
  (`CHANGES_REQUESTED` or `COMMENTED` with non-empty body, no inline
46
48
  threads). Parse body for actionable findings. Apply the
47
49
  `pr-fix-protocol` skill (`../../pr-fix-protocol/SKILL.md`), whose reply
48
50
  step for body-only findings posts a top-level review reply citing the
49
- new HEAD SHA → Step 3 in same tick. Reset
50
- `bugbot_clean_at = null` AND
51
- `copilot_clean_at = null`, `phase = BUGBOT`, Step 3 on new HEAD,
51
+ new HEAD SHA. Reset
52
+ `bugbot_clean_at = null`, `code_review_clean_at = null`, AND
53
+ `copilot_clean_at = null`, `phase = CODE_REVIEW`,
52
54
  schedule next wakeup, return. Convergence needs full
53
55
  back-to-back-clean on new HEAD.
54
56
  - **`classification == "clean"` (state `APPROVED`):** Set
@@ -78,14 +80,14 @@ Decide (four branches; match first whose predicate holds):
78
80
  `pull_request_review_id`:** Treat identically to gate (a) dirty+inline
79
81
  path — apply the `pr-fix-protocol` skill
80
82
  (`../../pr-fix-protocol/SKILL.md`). Reset
81
- `bugbot_clean_at = null` AND `copilot_clean_at = null`, `phase = BUGBOT`,
83
+ `bugbot_clean_at = null` AND `copilot_clean_at = null`, `phase = CODE_REVIEW`,
82
84
  schedule next wakeup, return.
83
85
  - **`classification == "dirty"` with empty inline comments matching
84
86
  `pull_request_review_id`:** Claude posted findings only in review body
85
87
  (`CHANGES_REQUESTED` or `COMMENTED` with non-empty body, no inline
86
88
  threads). Treat identically to gate (a) dirty+body path — apply the
87
89
  `pr-fix-protocol` skill (`../../pr-fix-protocol/SKILL.md`). Reset
88
- `bugbot_clean_at = null` AND `copilot_clean_at = null`, `phase = BUGBOT`,
90
+ `bugbot_clean_at = null` AND `copilot_clean_at = null`, `phase = CODE_REVIEW`,
89
91
  schedule next wakeup, return.
90
92
  - **`classification == "clean"` (state `APPROVED`):** Record evidence:
91
93
  "Claude APPROVED at <SHA>". Continue to gate (c).
@@ -111,8 +113,9 @@ Persist `mergeable_state` into `merge_state_status`. Decide:
111
113
  ([`../../rebase/SKILL.md`](../../rebase/SKILL.md)) Phase 1–4 against PR's
112
114
  base ref. After rebase + force-with-lease push, new HEAD invalidates
113
115
  every prior clean state — reset `bugbot_clean_at = null`,
114
- `copilot_clean_at = null`, `merge_state_status = null`, `phase = BUGBOT`,
115
- Step 3 on new HEAD, schedule next wakeup, return. Loop re-runs from
116
+ `code_review_clean_at = null`, `copilot_clean_at = null`,
117
+ `merge_state_status = null`, `phase = CODE_REVIEW`,
118
+ schedule next wakeup, return. Loop re-runs from
116
119
  scratch on new HEAD.
117
120
  - **`mergeable_state` is `"blocked"`, `"behind"`, `"unknown"`, or `"unstable"` for
118
121
  non-conflict reasons** (required checks pending/failing for "unstable",
@@ -157,7 +160,7 @@ against `current_head`. Decide:
157
160
  - `state: CHANGES_REQUESTED` or `COMMENTED` with non-empty body → dirty.
158
161
  Treat identically to gate (a) dirty path — spawn Agent (subagent_type: clean-coder) to fix,
159
162
  reset `bugbot_clean_at = null` AND `copilot_clean_at = null`,
160
- `phase = BUGBOT`, schedule next wakeup, return.
163
+ `phase = CODE_REVIEW`, schedule next wakeup, return.
161
164
  - **No Copilot review at `current_head` yet:** Record evidence: "No Copilot
162
165
  review at <SHA> (wait count: <N>)". Increment `copilot_wait_count`
163
166
  (init 0 on first COPILOT_WAIT entry; reset to 0 on every push and on every
@@ -187,7 +190,7 @@ Decide:
187
190
  `pr-fix-protocol` skill's unresolved-thread sweep
188
191
  (`../../pr-fix-protocol/SKILL.md`). Push if any code changed → reset
189
192
  `bugbot_clean_at = null` AND `copilot_clean_at = null`,
190
- `phase = BUGBOT`, schedule next wakeup, return. If only resolutions
193
+ `phase = CODE_REVIEW`, schedule next wakeup, return. If only resolutions
191
194
  (no code changes), re-check this gate without resetting.
192
195
 
193
196
  ## (f) Mark ready and report
@@ -4,40 +4,60 @@ Worked examples for `pr-converge`. Read on demand when a tick's
4
4
  classification is novel or ambiguous against the in-skill rules. Cross-refs
5
5
  into `SKILL.md` use `§Section name` notation.
6
6
 
7
- <example> User: `/pr-converge` Claude: [PR context + one tick bugbot/bugteam
8
- work; Step 4 per `workflows/schedule-wakeup-loop.md` default loop until
9
- convergence or stop]
7
+ <example> User: `/pr-converge` Claude: [PR context + one tick of internal
8
+ code-review/bugteam work, then the terminal Bugbot and Copilot gates; Step 4
9
+ per `workflows/schedule-wakeup-loop.md` — default loop until convergence or
10
+ stop]
10
11
  </example>
11
12
 
12
- <example> BUGBOT tick, latest bugbot review against older commit. Claude:
13
- [posts `bugbot run`, sets `bugbot_clean_at = null`, Step 4 per
14
- `workflows/schedule-wakeup-loop.md` (e.g. 270s wakeup), returns]
13
+ <example> CODE_REVIEW tick (the entry phase), the static sweep raises a
14
+ `ruff` failure on a changed file. Claude: [fixes it TDD, one commit, pushes,
15
+ resets `bugbot_clean_at = null` and `code_review_clean_at = null`, stays
16
+ `phase = CODE_REVIEW`, Step 4 at 270s, re-runs the sweep next tick]
15
17
  </example>
16
18
 
17
- <example> BUGBOT tick, bugbot has 2 unaddressed findings on HEAD. Claude:
18
- [TDD-fixes both, one commit, pushes, replies inline on both threads, posts
19
- `bugbot run`, Step 4 at 270s, returns]
19
+ <example> CODE_REVIEW tick, static sweep clean, `/code-review high --fix`
20
+ applies fixes to the working tree. Claude: [commits the applied fixes in one
21
+ commit, pushes, resets `bugbot_clean_at = null` and `code_review_clean_at =
22
+ null`, stays `phase = CODE_REVIEW`, Step 4 at 270s, returns]
20
23
  </example>
21
24
 
22
- <example> BUGBOT tick, bugbot clean against HEAD. Claude: [sets
23
- `bugbot_clean_at = HEAD`, `phase = CODE_REVIEW`, runs `/code-review --fix`
24
- in same tick]
25
+ <example> CODE_REVIEW tick, static sweep clean and `/code-review high --fix`
26
+ clean (no changes applied). Claude: [sets `code_review_clean_at = HEAD`,
27
+ `phase = BUGTEAM`, runs `Skill({skill: "bugteam", ...})` in same tick]
25
28
  </example>
26
29
 
27
- <example> CODE_REVIEW tick, `/code-review --fix` applies fixes to the
28
- working tree. Claude: [commits the applied fixes in one commit, pushes,
29
- resets `bugbot_clean_at = null` and `code_review_clean_at = null`, posts
30
- `bugbot run`, `phase = BUGBOT`, Step 4 at 270s, returns]
30
+ <example> BUGTEAM phase, bugteam pushed a fix commit during its run. Claude:
31
+ [re-resolves HEAD, resets `bugbot_clean_at = null` and `code_review_clean_at =
32
+ null`, `phase = CODE_REVIEW`, Step 4 at 270s, re-enters the internal passes on
33
+ the new HEAD]
31
34
  </example>
32
35
 
33
- <example> CODE_REVIEW tick, `/code-review --fix` clean (no changes
34
- applied). Claude: [sets `code_review_clean_at = HEAD`, `phase = BUGTEAM`,
35
- runs `Skill({skill: "bugteam", ...})` in same tick]
36
+ <example> BUGTEAM phase, bugteam reports convergence with no push. Claude:
37
+ [the internal passes are clean on `current_head`; `phase = BUGBOT` — routes into
38
+ the terminal Bugbot gate in the same tick]
36
39
  </example>
37
40
 
38
- <example> BUGTEAM phase, bugteam reports convergence and `bugbot_clean_at
39
- == current_head` (no push). Claude: [back-to-back clean necessary, not
40
- sufficient. Runs `convergence-gates.md` gates in order:
41
+ <example> Terminal BUGBOT gate, Bugbot disabled for the run (the default).
42
+ Claude: [availability gate exits 0, sets `bugbot_down = true`, advances to the
43
+ `convergence-gates.md` gates with the Bugbot gate bypassed — no trigger, no
44
+ wait, no agent]
45
+ </example>
46
+
47
+ <example> Terminal BUGBOT gate, Bugbot enabled and clean on HEAD. Claude:
48
+ [sets `bugbot_clean_at = HEAD`, advances to the `convergence-gates.md` gates in
49
+ the same tick]
50
+ </example>
51
+
52
+ <example> Terminal BUGBOT gate, Bugbot has 2 unaddressed findings on HEAD.
53
+ Claude: [TDD-fixes both, one commit, pushes, replies inline on both threads,
54
+ resets `bugbot_clean_at = null` and `code_review_clean_at = null`, `phase =
55
+ CODE_REVIEW`, Step 4 at 270s, re-enters the internal passes on the new HEAD]
56
+ </example>
57
+
58
+ <example> Convergence gates after the terminal Bugbot gate confirms
59
+ (`bugbot_clean_at == current_head`). Claude: [runs `convergence-gates.md` gates
60
+ in order:
41
61
  Gate (a): two calls — `pull_request_read(method="get_reviews")` +
42
62
  `pull_request_read(method="get_review_comments")`
43
63
  → filter Copilot → APPROVED at `current_head`
@@ -53,7 +73,7 @@ sufficient. Runs `convergence-gates.md` gates in order:
53
73
  → schedule next wakeup, return.
54
74
  Next tick: re-run gate (a) fetch → Copilot `APPROVED` at `current_head`
55
75
  → set `copilot_clean_at = current_head`, record evidence: "Copilot
56
- APPROVED at <SHA>", set `phase = BUGTEAM`, re-validate gates (b) and (c).
76
+ APPROVED at <SHA>", re-validate gates (b) and (c).
57
77
  Gate (e): the `pr-fix-protocol` unresolved-thread sweep
58
78
  (`../../pr-fix-protocol/SKILL.md`) → zero across PR → record evidence.
59
79
  Gate (f): all six gates pass → `update_pull_request(pullNumber=NUMBER,
@@ -64,40 +84,35 @@ mergeable_state clean, copilot CLEAN at <SHA>, claude absent at <SHA>,
64
84
  applies **Convergence** from `workflows/schedule-wakeup-loop.md`]
65
85
  </example>
66
86
 
67
- <example> BUGTEAM phase, bugteam pushed fix commit during run. Claude:
68
- [re-resolves HEAD, sets `bugbot_clean_at = null`, posts `bugbot run` in
69
- same tick, `phase = BUGBOT`, Step 4 at 270s]
70
- </example>
71
-
72
- <example> BUGBOT tick, review body says "found 3 potential issues" against
73
- HEAD but inline API returns zero matching for `current_head`. Claude:
74
- [increments `inline_lag_streak` to 1, Step 4 inline-lag rules (90s
75
- `ScheduleWakeup`), returns]
87
+ <example> CODE_REVIEW tick, review body says "found 3 potential issues"
88
+ against HEAD (a stale prior finding) but the diff is clean. Claude: [the static
89
+ sweep and `/code-review high --fix` both pass, sets `code_review_clean_at =
90
+ HEAD`, `phase = BUGTEAM`]
76
91
  </example>
77
92
 
78
- <example> Back-to-back clean reached, but `mergeStateStatus: DIRTY` (base
93
+ <example> Convergence gates reached, but `mergeStateStatus: DIRTY` (base
79
94
  advanced, merge conflicts). Claude: [runs §Convergence gate (c); does NOT
80
95
  mark ready; invokes `rebase` skill per `../../rebase/SKILL.md` Phase 1–4;
81
96
  after force-with-lease push, resets `bugbot_clean_at = null`,
82
- `copilot_clean_at = null`, `merge_state_status = null`, `phase = BUGBOT`,
83
- posts `bugbot run` on new HEAD, schedules next wakeup]
97
+ `code_review_clean_at = null`, `copilot_clean_at = null`, `merge_state_status
98
+ = null`, `phase = CODE_REVIEW`, schedules next wakeup]
84
99
  </example>
85
100
 
86
- <example> Back-to-back clean, mergeability CLEAN, Copilot review at
101
+ <example> Convergence gates reached, mergeability CLEAN, Copilot review at
87
102
  `current_head` `state == "CHANGES_REQUESTED"` with two unaddressed inline
88
103
  findings. Claude: [runs §Convergence gates (a); applies Fix protocol (TDD
89
- test → fix → push → reply inline both threads), resets `bugbot_clean_at`
90
- and `copilot_clean_at` null, `phase = BUGBOT`, posts `bugbot run` on new
91
- HEAD, schedules next wakeup]
104
+ test → fix → push → reply inline both threads), resets `bugbot_clean_at`,
105
+ `code_review_clean_at`, and `copilot_clean_at` null, `phase = CODE_REVIEW`,
106
+ schedules next wakeup, re-enters the internal passes on the new HEAD]
92
107
  </example>
93
108
 
94
- <example> Back-to-back clean, mergeability CLEAN, no Copilot review on
109
+ <example> Convergence gates reached, mergeability CLEAN, no Copilot review on
95
110
  `current_head`. Claude sets `phase = COPILOT_WAIT`, runs gate (d):
96
111
  `request_copilot_review(owner=OWNER, repo=REPO, pullNumber=NUMBER)`,
97
112
  schedules next wakeup, returns. Next tick:
98
113
  Copilot review `state: APPROVED` at `current_head`. Claude: [re-runs
99
114
  gate (a) fetch → APPROVED → sets `copilot_clean_at = current_head`,
100
- records evidence: "Copilot APPROVED at <SHA>", sets `phase = BUGTEAM`;
115
+ records evidence: "Copilot APPROVED at <SHA>";
101
116
  re-validates gates (b) Claude absent and (c) mergeability clean,
102
117
  records evidence for both; gate (e) — the `pr-fix-protocol`
103
118
  unresolved-thread sweep — passes trivially, record evidence:
@@ -108,12 +123,13 @@ at <SHA>, bugteam CLEAN at <SHA>, mergeable_state clean, copilot CLEAN at
108
123
  <SHA>, claude absent at <SHA>, 0 unresolved threads across PR; marked ready for review"]
109
124
  </example>
110
125
 
111
- <example> Back-to-back clean, mergeability CLEAN, post-convergence Copilot
112
- review returned `state: CHANGES_REQUESTED` with inline findings on
126
+ <example> Convergence gates reached, mergeability CLEAN, post-convergence
127
+ Copilot review returned `state: CHANGES_REQUESTED` with inline findings on
113
128
  `current_head`. Claude: [does NOT mark PR ready — gate (d) failed;
114
129
  applies Fix protocol on every confirmed Copilot finding (TDD test → fix →
115
- push → reply inline on each thread); resets `bugbot_clean_at = null` and
116
- `copilot_clean_at = null`; `phase = BUGBOT`; posts `bugbot run` on new
117
- HEAD; schedules next wakeup. Full back-to-back-clean cycle plus all six
118
- gates must hold again on new HEAD.]
130
+ push → reply inline on each thread); resets `bugbot_clean_at = null`,
131
+ `code_review_clean_at = null`, and `copilot_clean_at = null`; `phase =
132
+ CODE_REVIEW`; schedules next wakeup, re-enters the internal passes on the new
133
+ HEAD. Full back-to-back-clean cycle plus all six gates must hold again on new
134
+ HEAD.]
119
135
  </example>
@@ -8,7 +8,7 @@ sequence in `../../../_shared/pr-loop/fix-protocol.md`. Hook handling
8
8
  per [ground-rules.md](ground-rules.md).
9
9
 
10
10
  This file holds only the pr-converge deltas: the multi-PR teammate
11
- obligations and the same-tick re-trigger rule.
11
+ obligations and the same-tick re-entry rule.
12
12
 
13
13
  **Multi-PR (`state.json`) teammate obligations** (plus TDD, commit, push):
14
14
 
@@ -17,21 +17,21 @@ obligations and the same-tick re-trigger rule.
17
17
  (what changed + commit identifier), matching §Audit result → fix worker step 4 — **before** writing
18
18
  `state.json` and going idle.
19
19
  - Writes `last_action: "fix_pushed"`, `current_head: <new SHA>`,
20
- `bugbot_clean_at: null`, `bugbot_down: false`, `phase: "BUGBOT"`,
21
- `status: "awaiting_bugbot"`, `last_updated` (ISO-8601 UTC) to
22
- `state.json` (per §Concurrency).
23
- - Goes idle. Orchestrator spawns follow-up `general-purpose` agent for
24
- bugbot trigger and monitoring.
20
+ `bugbot_clean_at: null`, `code_review_clean_at: null`, `bugbot_down: false`,
21
+ `phase: "CODE_REVIEW"`, `status: "awaiting_code_review"`, `last_updated`
22
+ (ISO-8601 UTC) to `state.json` (per §Concurrency).
23
+ - Goes idle. Orchestrator spawns a follow-up `general-purpose` agent for the
24
+ CODE_REVIEW re-entry on the new HEAD.
25
25
 
26
- Orchestrator does not reply inline, trigger bugbot, or read repo source
26
+ Orchestrator does not reply inline, re-enter code-review, or read repo source
27
27
  files during fix phase in multi-PR mode.
28
28
 
29
- ### Same-tick re-trigger rule
29
+ ### Same-tick re-entry rule
30
30
 
31
- **After pushing a fix, always run Step 3 (`bugbot run`) in the same
32
- tick** regardless of phase. A new commit **resets the full convergence
33
- cycle**: a bugbot clean and a bugteam clean on an older SHA do **not**
34
- count toward convergence on the new `HEAD`. Re-obtain bugbot CLEAN on
35
- `current_head`, then bugteam CLEAN on the same `HEAD` with no
36
- intervening push. Re-triggering in the same tick saves a wakeup cycle
37
- vs deferring Step 3.
31
+ **After pushing a fix, re-enter the CODE_REVIEW phase in the same tick**
32
+ regardless of phase. A new commit **resets the full convergence cycle**: a
33
+ code-review clean, a bugteam clean, and a Bugbot clean on an older SHA do
34
+ **not** count toward convergence on the new `HEAD`. Re-run the static sweep and
35
+ `/code-review high --fix` on `current_head`, then bugteam, then the terminal
36
+ Bugbot gate, all on the same `HEAD` with no intervening push. Re-entering in the
37
+ same tick saves a wakeup cycle.
@@ -1,24 +1,28 @@
1
1
  # Ground rules
2
2
 
3
+ - **Internal-first.** The internal code-review and bugteam passes drive the code
4
+ to clean each tick; Cursor Bugbot and Copilot run only after that, as terminal
5
+ confirmation gates.
3
6
  - **Append commits.** Each tick adds at most one fix commit.
4
- - **Bugbot findings on current SHA mean fix-then-push-then-`bugbot run`,
5
- not another naked `bugbot run`.**
7
+ - **Bugbot findings on the current SHA mean fix-then-push-then-re-enter
8
+ CODE_REVIEW,** so the internal passes re-clear the new HEAD before the terminal
9
+ Bugbot gate runs again.
6
10
  - **All `*_clean_at`, `merge_state_status`, and `bugbot_down` reset on every push.**
7
11
  - **`bugbot run` comment is load-bearing.** Literal phrase exactly —
8
12
  empirically the only re-trigger Cursor Bugbot recognizes.
9
- - **Production edits go through `clean-coder`, except `/code-review --fix`.**
13
+ - **Production edits go through `clean-coder`, except `/code-review high --fix`.**
10
14
  The lead never hand-edits production files. Every bugbot, bugteam,
11
15
  Copilot, or Claude finding spawns `Agent(subagent_type="clean-coder")` to
12
- implement the fix. The CODE_REVIEW phase is the one exception: `/code-review
13
- --fix` applies its own findings to the working tree, which the next
14
- BUGBOT/BUGTEAM cycle re-reviews after the loop resets.
16
+ apply the fix. The CODE_REVIEW phase is the one exception: `/code-review
17
+ high --fix` applies its own findings to the working tree, which the next
18
+ CODE_REVIEW/BUGTEAM cycle re-reviews after the loop resets.
15
19
  - **Adapt when reality contradicts on-disk state.** If `state.json`,
16
20
  `git`, or `gh` disagree with live PR, escalate as hard blocker per
17
21
  [stop-conditions.md](stop-conditions.md).
18
22
  - **Cross-repo cwd routing is routine, not a fork.** When the PR under
19
23
  convergence lives in a different repo than the session is rooted in, route
20
24
  the working directory into a checkout of the PR's repo automatically —
21
- `/code-review --fix`, `git`, and every `clean-coder` fix spawn act on the
25
+ `/code-review high --fix`, `git`, and every `clean-coder` fix spawn act on the
22
26
  repo of the current working directory. The resolution is fixed
23
27
  ([per-tick.md § Step 1.5](per-tick.md)): resolve the PR worktree, `cd` into
24
28
  it, run local work there. Do not pause, ask, or raise it as a material fork.