// features — man bisect
> Everything is a repro.
bisect's one opinion: a bug you can replay is a bug you can find. Every feature below exists to turn a vague failure into a deterministic check, then spend as few replays as possible finding where it started.
// 01 — deterministic replay
> The flake killer
Replays run in ephemeral sandboxes with frozen clocks, pinned dependency trees, seeded randomness, and record-replay network. A failure either reproduces three of three times or bisect refuses to hunt — it will not bisect noise.
- + frozen time & TZ · seeded PRNG · pinned lockfiles
- + HTTP/gRPC record-replay with secret redaction
- + database snapshots via copy-on-write branches
$ bisect repro --verify 3
> clock frozen @ 2026-07-11T02:47:00Z · seed 4021
> run 1/3 … fail (DecimalError, line 214)
> run 2/3 … fail (identical stack)
> run 3/3 … fail (identical stack)
✓ deterministic — safe to bisect
// 02 — the bisection engine
> window v418..v465 · 47 commits · 9 authors
> ownership prune: touching billing/ or lib/money → 12
> semantic prune: docs/CI-only diffs dropped → 9
> replay v441 pass · v453 fail · v447 fail · v444 pass
✓ a1f9c3e isolated · 4 replays instead of 47
# cost: $0.31 in replay compute
> Spend replays like they cost money
Naive git-bisect replays log₂(n) commits. bisect does better: it prunes by code ownership and semantic diff first, so most hunts touch a handful of candidates. Every replay's verdict, cost, and duration is printed as it happens — no spinners hiding the work.
// median hunt: 5 replays, 6m 40s, under a dollar
// 03 — fix drafting
> Diffs with receipts
newOnce the causing commit is isolated, bisect drafts the minimal counter-patch and — always — the regression test that fails on the broken revision and passes on the fix. Both land in a draft PR assigned to whoever you choose. The agent has no push access to protected branches, by construction.
- + minimal diff bias: median patch is 11 lines
- + test-first: no test, no PR — configurable, default on
- + style-matched to the surrounding file, not the model
@@ -211,7 +211,9 @@ class TaxService:
- return round(subtotal * rate, 2)
+ cents = (subtotal * rate).quantize(
+ CENT, rounding=ROUND_HALF_EVEN)
+ return cents
# + test_half_cent_carry.py (fails on a1f9c3e, passes here)
// 04 — ci sentinel
> main went red @ 14:32 (test_invoice_totals)
> auto-hunt started · window: 6 commits since green
✓ root cause posted to #eng-payments @ 14:39
> draft PR waiting on @tomash · main auto-revert offered
> Red main, already handled
The sentinel subscribes to your CI. The moment a protected branch fails, it opens a hunt with the merge window as its search space — usually a handful of commits — and posts the verdict to the channel your team already argues in. Revert or fix-forward stays a human call.
- + GitHub Actions · GitLab CI · Buildkite · CircleCI
- + Slack & PagerDuty verdict delivery
- + per-repo budgets: max replays, max spend, quiet hours
// 05 — what the agent may touch
Capability boundaries are enforced by the sandbox, not by prompt. This table is the actual policy file, rendered.
| capability | scope | allowed |
|---|---|---|
| read repository | full history, all branches | ✓ yes |
| run code | ephemeral sandbox only, no prod credentials | ✓ yes |
| open draft PRs | feature branches, always draft | ✓ yes |
| push to protected branches | never — no token scope exists for it | ✗ no |
| reach production systems | replays use recorded traffic, not live services | ✗ no |
| retain your code | sandboxes destroyed post-hunt; zero training | ✗ no |
// 06 — plugs into
> Try it on your worst bug.
First hunt free. If bisect can't reproduce it, it tells you that too.