claude-dev-env 1.44.0 → 1.46.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.
- package/CLAUDE.md +9 -0
- package/_shared/pr-loop/scripts/code_rules_gate.py +426 -85
- package/_shared/pr-loop/scripts/pr_loop_shared_constants/code_rules_gate_constants.py +20 -0
- package/_shared/pr-loop/scripts/pr_loop_shared_constants/reviews_disabled_constants.py +1 -0
- package/_shared/pr-loop/scripts/reviews_disabled.py +82 -9
- package/_shared/pr-loop/scripts/tests/test_code_rules_gate.py +630 -21
- package/_shared/pr-loop/scripts/tests/test_code_rules_gate_constants.py +15 -0
- package/_shared/pr-loop/scripts/tests/test_reviews_disabled.py +57 -0
- package/agents/clean-coder.md +7 -1
- package/agents/code-quality-agent.md +8 -5
- package/hooks/blocking/code_rules_enforcer.py +1562 -37
- package/hooks/blocking/content_search_zoekt_redirect_guidance.py +19 -0
- package/hooks/blocking/open_questions_in_plans_blocker.py +249 -0
- package/hooks/blocking/test_code_rules_enforcer.py +1389 -0
- package/hooks/blocking/test_code_rules_enforcer_banned_noun_word.py +292 -0
- package/hooks/blocking/test_code_rules_enforcer_cap_meta.py +46 -8
- package/hooks/blocking/test_code_rules_enforcer_exempt_marker_chained.py +189 -0
- package/hooks/blocking/test_code_rules_enforcer_function_length.py +210 -0
- package/hooks/blocking/test_code_rules_enforcer_tests_isolate_home_temp.py +1512 -0
- package/hooks/blocking/test_code_rules_enforcer_unused_imports.py +9 -5
- package/hooks/blocking/test_content_search_to_zoekt_redirector_unit.py +30 -0
- package/hooks/blocking/test_open_questions_in_plans_blocker.py +790 -0
- package/hooks/hooks.json +10 -0
- package/hooks/hooks_constants/banned_identifiers_constants.py +19 -0
- package/hooks/hooks_constants/code_rules_enforcer_constants.py +129 -2
- package/hooks/hooks_constants/open_questions_in_plans_blocker_constants.py +35 -0
- package/hooks/hooks_constants/test_open_questions_in_plans_blocker_constants.py +125 -0
- package/package.json +1 -1
- package/skills/_shared/pr-loop/scripts/_path_resolver.py +34 -13
- package/skills/_shared/pr-loop/scripts/init_loop_state.py +1 -2
- package/skills/_shared/pr-loop/scripts/teardown_worktrees.py +1 -4
- package/skills/_shared/pr-loop/scripts/test__path_resolver.py +57 -0
- package/skills/_shared/pr-loop/scripts/test_init_loop_state.py +48 -0
- package/skills/_shared/pr-loop/scripts/test_teardown_worktrees.py +59 -0
- package/skills/bugteam/PROMPTS.md +48 -12
- package/skills/bugteam/reference/team-setup.md +4 -2
- package/skills/bugteam/scripts/bugteam_code_rules_gate.py +487 -76
- package/skills/bugteam/scripts/bugteam_scripts_constants/bugteam_code_rules_gate_constants.py +22 -1
- package/skills/bugteam/scripts/test_bugteam_code_rules_gate.py +602 -12
- package/skills/pr-converge/SKILL.md +5 -0
- package/skills/pr-converge/reference/per-tick.md +14 -5
- package/skills/pr-converge/reference/state-schema.md +7 -3
- package/skills/pr-converge/scripts/check_convergence.py +27 -1
- package/skills/pr-converge/scripts/test_check_convergence.py +28 -0
|
@@ -49,6 +49,16 @@ Capture `number`, `head.sha` (= `current_head`), owner/repo, branch.
|
|
|
49
49
|
|
|
50
50
|
### `phase == BUGBOT`
|
|
51
51
|
|
|
52
|
+
**Opt-out gate (runs first, before any fetch or trigger).**
|
|
53
|
+
`python "$HOME/.claude/_shared/pr-loop/scripts/reviews_disabled.py" --reviewer bugbot`
|
|
54
|
+
|
|
55
|
+
- Exit 0 (`CLAUDE_REVIEWS_DISABLED` lists `bugbot`) → set `bugbot_down = true`,
|
|
56
|
+
`phase = BUGTEAM`, continue BUGTEAM in the same tick; skip steps a–c below.
|
|
57
|
+
- Exit 1 → proceed to step a.
|
|
58
|
+
|
|
59
|
+
Because `bugbot_down` resets on every push, this gate re-runs on every
|
|
60
|
+
BUGBOT entry and keeps Cursor Bugbot skipped for the entire run.
|
|
61
|
+
|
|
52
62
|
a. Fetch Cursor Bugbot reviews newest-first, walk back until first clean:
|
|
53
63
|
|
|
54
64
|
```
|
|
@@ -207,11 +217,10 @@ BUGBOT.
|
|
|
207
217
|
|
|
208
218
|
## Step 3: Re-trigger bugbot
|
|
209
219
|
|
|
210
|
-
- [ ] **Opt-out gate.**
|
|
211
|
-
|
|
212
|
-
`bugbot_down = true
|
|
213
|
-
|
|
214
|
-
`bugbot_down` exactly the way it does when bugbot CI is unavailable.
|
|
220
|
+
- [ ] **Opt-out gate.** Enforced at BUGBOT entry (see `### phase == BUGBOT`).
|
|
221
|
+
When `CLAUDE_REVIEWS_DISABLED` lists `bugbot`, the entry gate sets
|
|
222
|
+
`bugbot_down = true` and routes to BUGTEAM before any trigger flow runs,
|
|
223
|
+
so the checks below are skipped.
|
|
215
224
|
- [ ] **Silent-pass pre-check.** Run `python ~/.claude/skills/pr-converge/scripts/check_bugbot_ci.py --check-clean --owner <O> --repo <R> --sha <current_head>`
|
|
216
225
|
- [ ] Exit 0 → bugbot CI completed clean with no review (silent pass); set `bugbot_clean_at = current_head`, `phase = BUGTEAM`, continue BUGTEAM same tick
|
|
217
226
|
- [ ] Exit 1 (not a silent pass) or Exit 2 (gh CLI error — silent pass not confirmable) → continue with the trigger flow below
|
|
@@ -23,9 +23,13 @@ live ONLY in the single-PR `$CLAUDE_JOB_DIR/pr-converge-state.json` file
|
|
|
23
23
|
matching. Reset to `0` on any other branch outcome.
|
|
24
24
|
- `bugbot_down`: boolean, init `false`. Set `true` when bugbot fails to
|
|
25
25
|
acknowledge a trigger comment; forces phase to BUGTEAM. Also set `true`
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
26
|
+
at every BUGBOT-phase entry when `CLAUDE_REVIEWS_DISABLED` lists the
|
|
27
|
+
`bugbot` token (env opt-out via the BUGBOT entry gate in `per-tick.md`),
|
|
28
|
+
which routes straight to BUGTEAM before any bugbot fetch or trigger. Also
|
|
29
|
+
set `true` when an acknowledged trigger has been outstanding more than 30
|
|
30
|
+
minutes with no surfaced review at `current_head` (per Step 2 BUGBOT (c)
|
|
31
|
+
30-minute budget — see `per-tick.md`). Reset to `false` on every push;
|
|
32
|
+
the entry gate re-applies the env opt-out on the next BUGBOT entry.
|
|
29
33
|
Once set, remains `true` until the next push; if bugbot stays down
|
|
30
34
|
across ticks, the flag persists and BUGTEAM continues.
|
|
31
35
|
- `bugbot_acknowledged_at`: ISO 8601 timestamp string or `null`. Records
|
|
@@ -4,6 +4,10 @@ Usage:
|
|
|
4
4
|
python scripts/check_convergence.py --owner <O> --repo <R> --pr-number <N>
|
|
5
5
|
[--bugbot-down]
|
|
6
6
|
|
|
7
|
+
The bugbot check-run gate is bypassed when either ``--bugbot-down`` is
|
|
8
|
+
passed OR the ``CLAUDE_REVIEWS_DISABLED`` environment variable lists the
|
|
9
|
+
``bugbot`` token, so a Bugbot opt-out closes the gate without the flag.
|
|
10
|
+
|
|
7
11
|
Exit codes:
|
|
8
12
|
0 — all pre-conditions met
|
|
9
13
|
1 — one or more conditions not met (FAIL lines printed to stdout)
|
|
@@ -48,6 +52,14 @@ from pr_converge_skill_constants.constants import (
|
|
|
48
52
|
UNRESOLVED_THREAD_DETAIL_MAX,
|
|
49
53
|
)
|
|
50
54
|
|
|
55
|
+
_shared_pr_loop_scripts_dir = (
|
|
56
|
+
Path(__file__).absolute().parents[3] / "_shared" / "pr-loop" / "scripts"
|
|
57
|
+
)
|
|
58
|
+
if str(_shared_pr_loop_scripts_dir) not in sys.path:
|
|
59
|
+
sys.path.insert(0, str(_shared_pr_loop_scripts_dir))
|
|
60
|
+
|
|
61
|
+
from reviews_disabled import is_bugbot_disabled_via_env
|
|
62
|
+
|
|
51
63
|
|
|
52
64
|
def _is_bugteam_review(review_body: str) -> bool:
|
|
53
65
|
"""Return True when a review body opens with a bugteam audit header.
|
|
@@ -621,6 +633,20 @@ def parse_arguments(all_argv: list[str]) -> argparse.Namespace:
|
|
|
621
633
|
return parser.parse_args(all_argv)
|
|
622
634
|
|
|
623
635
|
|
|
636
|
+
def _resolve_bugbot_down(bugbot_down_flag: bool) -> bool:
|
|
637
|
+
"""Combine the explicit flag with the CLAUDE_REVIEWS_DISABLED env opt-out.
|
|
638
|
+
|
|
639
|
+
Args:
|
|
640
|
+
bugbot_down_flag: Value of the ``--bugbot-down`` CLI flag.
|
|
641
|
+
|
|
642
|
+
Returns:
|
|
643
|
+
True when the flag is set OR ``CLAUDE_REVIEWS_DISABLED`` lists the
|
|
644
|
+
``bugbot`` token, so the env opt-out bypasses the bugbot gates even
|
|
645
|
+
when the caller omits the flag.
|
|
646
|
+
"""
|
|
647
|
+
return bugbot_down_flag or is_bugbot_disabled_via_env()
|
|
648
|
+
|
|
649
|
+
|
|
624
650
|
def main(all_arguments: list[str]) -> int:
|
|
625
651
|
"""Run the script end-to-end against parsed CLI arguments.
|
|
626
652
|
|
|
@@ -635,7 +661,7 @@ def main(all_arguments: list[str]) -> int:
|
|
|
635
661
|
owner=arguments.owner,
|
|
636
662
|
repo=arguments.repo,
|
|
637
663
|
number=getattr(arguments, "pr_number"),
|
|
638
|
-
bugbot_down=arguments.bugbot_down,
|
|
664
|
+
bugbot_down=_resolve_bugbot_down(arguments.bugbot_down),
|
|
639
665
|
)
|
|
640
666
|
|
|
641
667
|
|
|
@@ -217,6 +217,34 @@ def test_private_helpers_recognize_dirty_legacy_header_body() -> None:
|
|
|
217
217
|
assert check_convergence._is_clean_bugteam_review(DIRTY_LEGACY_BUGTEAM_BODY) is False
|
|
218
218
|
|
|
219
219
|
|
|
220
|
+
def should_resolve_bugbot_down_true_when_flag_set(
|
|
221
|
+
monkeypatch: pytest.MonkeyPatch,
|
|
222
|
+
) -> None:
|
|
223
|
+
monkeypatch.delenv("CLAUDE_REVIEWS_DISABLED", raising=False)
|
|
224
|
+
assert check_convergence._resolve_bugbot_down(True) is True
|
|
225
|
+
|
|
226
|
+
|
|
227
|
+
def should_resolve_bugbot_down_true_when_env_disables_bugbot(
|
|
228
|
+
monkeypatch: pytest.MonkeyPatch,
|
|
229
|
+
) -> None:
|
|
230
|
+
monkeypatch.setenv("CLAUDE_REVIEWS_DISABLED", "bugbot")
|
|
231
|
+
assert check_convergence._resolve_bugbot_down(False) is True
|
|
232
|
+
|
|
233
|
+
|
|
234
|
+
def should_resolve_bugbot_down_false_when_flag_unset_and_env_empty(
|
|
235
|
+
monkeypatch: pytest.MonkeyPatch,
|
|
236
|
+
) -> None:
|
|
237
|
+
monkeypatch.delenv("CLAUDE_REVIEWS_DISABLED", raising=False)
|
|
238
|
+
assert check_convergence._resolve_bugbot_down(False) is False
|
|
239
|
+
|
|
240
|
+
|
|
241
|
+
def should_resolve_bugbot_down_false_when_env_disables_only_bugteam(
|
|
242
|
+
monkeypatch: pytest.MonkeyPatch,
|
|
243
|
+
) -> None:
|
|
244
|
+
monkeypatch.setenv("CLAUDE_REVIEWS_DISABLED", "bugteam")
|
|
245
|
+
assert check_convergence._resolve_bugbot_down(False) is False
|
|
246
|
+
|
|
247
|
+
|
|
220
248
|
def should_bypass_bugbot_gates_when_bugbot_down_is_true(
|
|
221
249
|
monkeypatch: pytest.MonkeyPatch, capsys: pytest.CaptureFixture[str]
|
|
222
250
|
) -> None:
|