Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 19 additions & 1 deletion AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,24 @@ at the same time a Claude Code plugin, an Agent Plugins 1.0 plugin and a Codex
plugin; all three launch the same server with `uv run`. Both its users and its
maintainers are LLM agents inside harnesses; design for them first.

## Execution model

Work here is run by a lead that delegates first. The lead holds the architecture,
the specs and the merges; implementers take bounded, file-disjoint leaves in their
own worktrees, on the cheapest tier that finishes a leaf with the gates green.
Two currencies decide who does what. **Tokens**: the lead runs on the most capable
tier and everything it reads or edits itself stays in its context, re-sent on every
later turn of the cycle; an implementer's tokens are spent once, on a cheaper tier,
in a context discarded after its report. **Latency**: parallel leaves cost the
slowest leaf rather than the sum, but each dispatch carries a fixed overhead (the
brief, then the implementer's cold read of this file, its leaf and the cited
reports) that measured leaves place at 4–15 minutes (`KT-C`, `KT-D`). So delegation
is the default, and not stubborn: a leaf the lead finishes faster than it can brief
(scaffold, shared helpers, CI, this file, changelog) stays with the lead. Whatever
the harness offers for parallel workers instantiates this; with nothing, the lead
runs the same roadmap sequentially under the same discipline. Load the
`campaign-lead` dev skill before deciding a task is too small for it.

## Load the dev plugin

```bash
Expand All @@ -26,7 +44,7 @@ claude plugin install colgrep-mcp-dev@colgrep-mcp # from the repo's marketpla
| Skill | Load it when |
|:--|:--|
| `maintainer-policy` | you are about to add scaffold, CI, hooks, docs or a "best practice"; review or refactor server code; choose between `perf` and `refactor`; write a docstring |
| `campaign-lead` | you lead, plan or dispatch multi-agent work here: architecture report, roadmap, worktrees, reviewer pass, closing a cycle |
| `campaign-lead` | a task has, or might have, more than one lead-sized leaf — decide that inside the skill, not before it: architecture report, roadmap, worktrees, dispatch, reviewer pass, closing a cycle |
| `landing-and-release` | you commit, rebase, merge, open or land a PR, resolve a conflict, cut a release, or `cz check` rejects you |
| `stack-traps` | you run `colgrep` by hand, touch a handler or a manifest, debug a plugin that does not connect, read a Windows CI failure, or `claude -p` fails |

Expand Down
2 changes: 1 addition & 1 deletion dev/evals/campaign-lead-triggers/case.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ execution:
allowed_tools: [Read, Glob, Skill]
prompt: |
We just merged the knowledge-transfer report for the consistency campaign. Time to run
the next cycle on this repo with three Sonnet implementers working in parallel worktrees;
the next cycle on this repo with three implementers working in parallel worktrees;
here are the follow-ups from that retrospective to turn into roadmap leaves. Set it up and
get them dispatched.
graders:
Expand Down
37 changes: 28 additions & 9 deletions dev/skills/campaign-lead/SKILL.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
---
name: campaign-lead
description: "Guides a lead through running a multi-agent campaign on this repository: writing the architecture report, building the roadmap, creating worktrees by hand, dispatching implementers, merging per level, running a read-only reviewer, and closing with a knowledge-transfer report. Load this whenever asked to lead, coordinate, plan, or dispatch work on this repo, to create a roadmap or worktrees for subagents, to review a merged roadmap level, or to close out a campaign cycle — even if the request never says 'skill'."
description: "Guides a lead through running a multi-agent campaign on this repository: deciding what to delegate and what to keep, writing the architecture report, building the roadmap, creating worktrees by hand, dispatching implementers, merging per level, running a read-only reviewer, and closing with a knowledge-transfer report. Load this whenever asked to lead, coordinate, plan, or dispatch work on this repo, before deciding a task is too small to delegate, to create a roadmap or worktrees for implementers, to review a merged roadmap level, or to close out a campaign cycle — even if the request never says 'skill'."
---

# Campaign Lead
Expand All @@ -9,6 +9,21 @@ Composes with the machine-level `writing-reports`, `managing-roadmaps` and `writ
skills for mechanics; this skill is the order of operations and the rules this repository's
campaigns established, each cited to the retrospective that records it (`AGENTS.md` legend).

## The Default: Delegate First

`AGENTS.md` §Execution model states the contract; this section is how the lead applies it.
Every task that touches more than one file-disjoint leaf is a campaign, and every leaf goes to
an implementer unless the exception below applies. The lead's own context is the expensive
currency — it runs on the most capable tier and re-reads everything it touched on every later
turn — and wall-clock is the other: implementers run in parallel, so a level costs its slowest
leaf, while a dispatch carries a fixed overhead of the brief plus the implementer's cold read
of `AGENTS.md`, its leaf and the cited reports. Measured leaves ran 4–15 minutes each on the
cheaper tier (KT-C §Wins, KT-D §Wins); below that floor the lead is faster than its own brief.
Run implementers on the cheapest tier that clears the gates for leaves of that size; when one
leaf fails there, escalate that leaf, not the round. The harness instantiates the mechanism —
whatever it offers for parallel workers, in worktrees the lead created; with none, run the same
roadmap sequentially under the same discipline, and say so in the retrospective.

## Order of Operations

1. **Architecture report first** — contracts, file ownership per leaf, risks — under
Expand All @@ -20,9 +35,10 @@ campaigns established, each cited to the retrospective that records it (`AGENTS.
not-yet-shared helper duplicates it, and two duplicates collide at merge (KT-B §Wins,
KT-C §Wins: helpers before dispatch → zero conflicts).
4. **One worktree per leaf, created by hand**: `git worktree add <path> -b task/<leaf>
<campaign-branch>`. Never rely on the Agent tool's `isolation: worktree` for this — it
branches from the primary checkout's `main`, not the campaign branch, and a whole dispatch
round lands on the wrong base (KT-H §Pain Points, KT-B §Root Causes).
<campaign-branch>`. Never let the harness create it — a harness convenience branches from
whatever it considers the default base, not the campaign branch, and a whole dispatch round
lands on the wrong base (KT-H §Pain Points, KT-B §Root Causes; the Claude Code instance of
this trap is `stack-traps` `references/claude-code.md#agent-worktree`).
5. **Dispatch** with `references/dispatch-prompt.md`. Every prompt states "stop if the leaf
file is missing from your worktree" — it turns a wrong-base worktree into a ~15-second
no-op with zero stray commits instead of wasted work (KT-H §Wins).
Expand All @@ -43,9 +59,11 @@ campaigns established, each cited to the retrospective that records it (`AGENTS.
is what closes a campaign with zero merge conflicts (KT-H, KT-C §Wins).
- **Hard stop time**, stated in both the leaf and the dispatch prompt: the lead merges whatever
is green at the stop (`consistency` roadmap README §Gotchas).
- **Do lead-sized leaves yourself.** Scaffolding, shared helpers, CI wiring, `AGENTS.md`,
changelog fixes: delegating them costs a dispatch round-trip for work the lead finishes in
minutes (KT-C, KT-H §Wins).
- **The exception to the default: do lead-sized leaves yourself.** Scaffolding, shared
helpers, CI wiring, `AGENTS.md`, changelog fixes: delegating them costs a dispatch round-trip
for work the lead finishes in minutes (`adapter_hygiene` took 4; KT-C, KT-H §Wins). The
exception is per leaf, never per cycle — a cycle with no dispatch at all needs the
retrospective to say why.
- **Refactor leaves need an explicit dump-and-diff oracle**, not "tests still pass": dump
`Client.list_tools()`/`list_resources()`/`list_resource_templates()`/`list_prompts()` JSON on
the base and the branch, diff empty. The MCP SDK ships docstrings verbatim, so even
Expand All @@ -55,8 +73,9 @@ campaigns established, each cited to the retrospective that records it (`AGENTS.
- **Windows CI is the only portability oracle here** — read its verdict, don't skim it,
whenever a leaf is the first to exercise a previously-untested path, and name that path in
the PR body (KT-C §Pain Points, CI).
- **A subagent that says it is "watching CI in the background" has already ended its turn.**
Make it block on `gh run watch --exit-status`, or read the run yourself.
- **An implementer's turn ends with its report.** Anything it says it will do "in the
background" after that never happens; make it block on the run (`gh run watch
--exit-status`) or read the run yourself (`stack-traps` `references/claude-code.md#worker-turn`).
- **A drift test that relates two artefacts owned by different leaves is red until both land.**
Order the roadmap so the *naming* side lands first (e.g. the `AGENTS.md` skill table before
the skill leaves it names), even ahead of BFS order, or every merge in between is red on a
Expand Down
9 changes: 7 additions & 2 deletions dev/skills/campaign-lead/references/dispatch-prompt.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@ shape to look complete:
the lead re-runs and compares rather than trusting a summary.
- **Commit rules and hard-stop time** keep the history and the time-box legible across many
parallel branches the lead did not watch being written in real time.
- **Tier is the lead's choice, not a template field.** Dispatch on the cheapest tier that has
cleared the gates for leaves of this size (`campaign-lead` §The Default); the final report's
gate-attempt count is the signal to escalate *that leaf* to a stronger tier on the next
round, not to stop delegating.

---

Expand Down Expand Up @@ -52,6 +56,7 @@ never edit versions by hand; never author a `release(...)` commit.
how each fact is cited, size caps, prohibited real-world side effects such as running a real
external tool or a live eval>.
**Final report** (your last message, plain text): the commits (hash + subject); the exact
output line of each gate; files touched outside your ownership (should be none) or changes you
recommend elsewhere; anything unfinished at the hard stop.
output line of each gate and how many attempts each took to go green; files touched outside
your ownership (should be none) or changes you recommend elsewhere; anything unfinished at the
hard stop.
```
5 changes: 4 additions & 1 deletion dev/skills/stack-traps/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ linked section, don't re-derive the trap from scratch.
| `claude -p` or `claude plugin eval` fails with an OAuth error | claude-code | `references/claude-code.md#oauth` |
| `claude --plugin-dir . mcp list` says Connected but your edit is not in the server, or the plugin fails right after a bump | claude-code | `references/claude-code.md#uvx-pin` |
| the plugin's hooks don't fire, or still run the old text, after an edit or an update; Codex lists them but never runs them | claude-code | `references/claude-code.md#plugin-hooks` |
| an implementer reports "leaf file missing", or its branch is based on `main` instead of the campaign branch | claude-code | `references/claude-code.md#agent-worktree` |
| a subagent said it was watching CI or would follow up, and nothing happened | claude-code | `references/claude-code.md#worker-turn` |
| a Bash command is blocked, including inside a heredoc that only mentions the search pattern | machine | `references/machine.md#shell-hook` |
| CI is red only on windows-latest, or only a `setup-uv` step fails | machine | `references/machine.md#windows-ci` |
| `git worktree add` on `main` fails because it's checked out elsewhere | machine | `references/machine.md#worktree-main` |
Expand Down Expand Up @@ -59,7 +61,8 @@ linked section, don't re-derive the trap from scratch.
- `references/claude-code.md` — root `.mcp.json` vs plugin-scope
`.claude-plugin/mcp.json`, marketplace vs plugin namespaces, `claude -p`
on an expired OAuth session, the `uvx colgrep-mcp==<version>` pin, plugin
hooks loading (reload, Codex trust, the portable/Claude-only split).
hooks loading (reload, Codex trust, the portable/Claude-only split), the
Agent tool's worktree base and the end of a subagent's turn.
- `references/machine.md` — the plugin's shell-search hook and `COLGREP_BYPASS=1`,
Windows CI's two known causes, the detached-worktree trick for `main`, the
permission classifier, a venv whose shebangs point at a moved checkout.
34 changes: 34 additions & 0 deletions dev/skills/stack-traps/references/claude-code.md
Original file line number Diff line number Diff line change
Expand Up @@ -128,3 +128,37 @@ so `uv run pytest tests/test_hooks.py` is the fastest check. Keep
Claude-only events (`WorktreeRemove`) in `hooks/claude-code.json`, never in
the portable `hooks/hooks.json` a Codex parser also reads;
`test_hooks.py` pins the split.

## An implementer's worktree is based on `main`, not the campaign branch {#agent-worktree}

**Symptom**: an implementer dispatched with the Agent tool reports "leaf file
missing" in its first minute, or its commits turn out to sit on a branch cut
from `main` while the roadmap, specs and helpers live on the campaign branch.

**Cause**: the Agent tool's `isolation: "worktree"` option creates the
worktree from the primary checkout's HEAD — `main` — never from the branch
the lead's session is on. One whole dispatch round landed on the wrong base
this way (`KT-H` §Pain Points, `KT-B` §Root Causes). This is the Claude Code
instance of the harness-neutral rule in `campaign-lead` step 4.

**What to do**: create every implementer worktree yourself, `git worktree
add <path> -b task/<leaf> <campaign-branch>`, and pass the path in the
dispatch prompt; never set `isolation: "worktree"` from a campaign branch.
Keep the "stop if the leaf file is missing" line in every prompt — it is what
turned the wrong-base round into a 15-second no-op.

## A subagent said it was watching CI, and nothing happened {#worker-turn}

**Symptom**: an implementer's final message says it is "watching CI in the
background" or "will follow up when the run finishes"; the run finishes red
or green and nothing follows.

**Cause**: an Agent-tool subagent's turn ends with its final message; there
is no later execution, so any promise about the future in that message is
never kept. The same holds for any harness whose workers return a single
report (`campaign-lead` §Rules).

**What to do**: make the implementer block inside its turn — `gh run watch
--exit-status <run-id>` — and paste the verdict line into its report, or read
the run yourself after the report. Never treat a worker's "watching" as a
gate result.