team-fix · git:20260903.8a010bb · 2026-09-03 · sha256 b5b5e934b2336d0a
team-fix git:20260903.8a010bbA
Immutable. This exact content is served forever at /api/v1/blob/b5b5e934b2336d0a.
---
name: team-fix
description: |
Compressed bug-fix pipeline — reproduce, write failing test, minimal fix,
verify, and open a draft PR. Skips Question/Research/Design/Structure/Plan
phases. Invoke ONLY on explicit pipeline intent — the user says "run the
bug-fix pipeline", "team-fix this bug", or runs "/team-fix". The pipeline
moves the tracker ticket, commits, pushes a branch, and opens a draft PR
without stopping to ask: never infer pipeline intent from a plain request
to fix a bug — that asks for an inline fix, not this pipeline.
effort: high
argument-hint: "<ticket id, issue URL, or bug description>"
---
# Team Fix — Bug Fix Pipeline
Run the compressed bug-fix pipeline. Goes straight to test-driven fix
discipline without the full QRSPI ceremony.
Invocation is guarded per `skills/principle-explicit-intent/SKILL.md`: the
pipeline fires only on stated pipeline intent — a plain "fix this bug" asks
for an inline fix, not this pipeline.
## Input
`$ARGUMENTS` may be:
- A ticket identifier (e.g. `ENG-1234`) — set aside as `ticketId` on
`task.md`.
- An issue URL — fetched through `gh issue view` to extract title and body.
- Free-form text — treated as the bug description.
When `$ARGUMENTS` is empty, **discover, do not demand**: ground in repo
context before asking. Read recent `git log` activity and the repo's
`README` / `CLAUDE.md` to surface the likely failing area, then use
`AskUserQuestion` with labeled options to fill any genuine gap. Never
bare-stop with a plain "describe the bug" demand when context is available.
## When to Use
Use `/team-fix` when:
- The bug is well-understood and the affected code is known
- The fix is likely contained to a small number of files
- No architectural decisions are needed — this is a defect correction
Use `/team` (full QRSPI pipeline) when:
- The root cause is unknown and needs investigation
- The fix requires designing new behavior or APIs
- Multiple subsystems may be involved
- The user wants to align on the approach before code is written
## Pipeline
```
WORKTREE → REPRODUCE → RED (failing test) → GREEN (minimal fix) → VERIFY → SHIP
```
No Question. No Research. No Design. No Structure. No Plan. No approval gate.
## Setup
1. **Resolve the input** to a bug description first. On empty `$ARGUMENTS`,
ground in repo context, then ask only for genuine gaps, per the
**"discover, do not demand"** rule in `## Input`. A ticket id or issue
URL is resolved as `## Input` describes (`gh issue view` for URLs).
2. **Move the ticket to in-progress.** If the input resolved to a ticket id
or issue, move that ticket to its tracker's in-progress state — this is
the first action of the fix, before any other work begins. Call the Skill
tool with `tracking-tickets` and
follow its ticket-lifecycle rules, best-effort —
skip silently when no tracker mechanism exists. Never block the pipeline
on a tracker update.
3. **Derive `<id>`** the same way `/team` does (ticket-prefixed or
date-prefixed kebab slug).
4. **Run the WORKTREE phase** (`## Worktree` below) before anything else
touches the working tree. It settles which branch the fix commits to, so
it must finish before the artifact directory is authored.
5. **Create `docs/plans/<id>/`** inside the resolved worktree, and write a
minimal `docs/plans/<id>/task.md` with the standard frontmatter
(`topic`, `date`, `phase: task`, `ticketId`) plus a brief description
of the bug. The `topic` value is the kebab portion of `<id>` — i.e.
`<id>` minus the `<TICKET>-` or `<YYYY-MM-DD>-` prefix. Never use the
ticket id, the date, or a re-worded description as the topic.
`ticketId` lives only on `task.md`. This is the single durable record
for the fix and lets any `/team-*` command pick it up if interrupted.
6. **Seed the TodoWrite ledger** with the bug-fix phases:
`Worktree → Reproduce → Red (failing test) → Green (minimal fix) → Verify → Ship`.
Mark `Worktree` as `in_progress`.
See `skills/principle-progress-tracking/SKILL.md` for the per-step tracking convention agents follow within each phase.
## Worktree
This is the **leading** phase, and the one hard gate in the pipeline. A fix
never commits to the default branch. Everything after this phase runs in the
checkout this phase resolves.
### Branch gate
Run this block first. It prints `on-default` when HEAD is the repository's
default branch, and `ok <branch>` otherwise:
```sh
# Branch gate — a fix never commits to the default branch.
default="$(git symbolic-ref --short refs/remotes/origin/HEAD 2>/dev/null)"
default="${default#origin/}"
if [ -z "$default" ]; then
# No origin/HEAD (no remote, or an unset remote head): fall back to whichever
# conventional default-branch name actually exists locally.
for candidate in main master; do
if git show-ref --verify --quiet "refs/heads/$candidate"; then
default="$candidate"; break
fi
done
fi
head="$(git rev-parse --abbrev-ref HEAD)"
if [ -n "$default" ] && [ "$head" = "$default" ]; then
echo "on-default"
else
echo "ok $head"
fi
```
- **`ok <branch>`** — HEAD is already on a non-default branch. Check
whether it is the head of an open pull request:
`gh pr view --json number,title --jq '"#\(.number) \(.title)"' 2>/dev/null`.
No open PR, or one whose title names this bug → reuse the branch in
place: create no worktree and no new branch, and announce the reuse
once: "Continuing on branch `<branch>`." This is also the linked-worktree
reuse case in `skills/team-worktree/SKILL.md` → "Detect existing
worktree". An open PR for other work → treat it as `on-default`: a fix
never rides on another PR's branch, so isolate per **Isolate** below.
- **`on-default`** — isolate before the first commit, per **Isolate** below.
### Isolate
Create the home worktree on branch `<id>` off `origin/HEAD`, exactly as
`/team`'s leading WORKTREE phase does. Call the Skill tool with
`team-worktree` for the single-repo
"Create the worktree(s)" procedure, and with `worktree-isolation` for the topology:
```sh
git fetch origin --quiet
git worktree add .claude/worktrees/<id> -b <id> origin/HEAD
```
Then continue the fix inside that worktree.
**Edge — branch `<id>` already exists** (re-invocation): reuse the worktree
that holds it. Do not recreate either one.
**Edge — worktree creation fails**, on a shallow clone, certain CI systems,
or permissions. Isolation is best-effort; **the branch is not.** Report the
failure loudly, then branch in place and keep going:
```sh
git switch -c <id>
```
Re-run the branch gate afterward. It must print `ok <id>`. If the run cannot
get off the default branch at all, stop and report — that is the one
condition that aborts before any work, because the alternative is committing
a fix to the default branch.
## Execution
Call the Skill tool with `test-driven-bug-fix` before proceeding, and follow that
methodology.
When the failure is non-obvious, call the Skill tool with
`systematic-debugging` and drill its
**Root Cause Analysis (5 Whys)** causal chain to the root before proposing a
fix. The fix lands at the root, never at the symptom, per
`skills/principle-fix-root-causes/SKILL.md`.
When the buggy behavior looks deliberate — a guard, a threshold, a
workaround, anything an author plausibly wrote on purpose — call the
Skill tool with `why` on that code before changing it. A "bug" that was a
deliberate trade-off needs its constraint preserved, not deleted; the
rationale findings become inputs to the minimal fix.
Mark each TodoWrite item `in_progress` when you begin and `completed`
when it finishes.
**Mechanical gate between Red and Green:** the new test must fail with an
assertion failure, not a crash, and the project's static checks (typecheck,
lint, build) must pass. Do not proceed to the fix until both are confirmed. A
runner that executes tests without type-checking them leaves a red type checker
behind a green suite.
## Ship
1. Commit in two commits:
- `test:` commit with the failing test
- `fix:` commit with the minimal fix
2. **Open a draft PR automatically — do not stop to ask.** The WORKTREE
phase already put the run on a non-default branch, so push that branch
and open the PR as a **draft** (`gh pr create --draft`). Re-assert the
branch gate first — `git rev-parse --abbrev-ref HEAD` must not name the
default branch. If it does, push nothing and report: the commits are
local and recoverable, a push to the default branch is not.
3. **Ticket — link now, in-review when ready.** If `ticketId` is non-null in
`task.md`'s frontmatter, call the Skill tool with `tracking-tickets` and
apply its ticket-lifecycle rules: link the PR to the ticket through the
conditional closing footer, keep the ticket in-progress while the PR is a
draft and move it to in-review only once the PR is marked ready for
review, and never close the ticket by hand — the link auto-closes it on
merge. Best-effort. Never block. Surface the `ticketId` in the completion
report.
4. Mark all TodoWrite items complete.
## Aborting
If reproduction fails: report "Bug could not be reproduced with the
given description." and stop. Do not write a test for an unconfirmed bug.
If the fix is larger than expected (touching many files, requiring new
APIs, or revealing an architectural problem): stop, report the scope,
and recommend switching to the full `/team` pipeline.