fanout-cli 0.8.0 → 0.9.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/README.md +8 -2
- package/dist/cli.js +0 -0
- package/dist/cli.js.map +4 -4
- package/dist/fake-agent.js +0 -0
- package/dist/fake-agent.js.map +2 -2
- package/package.json +9 -8
- package/plugin/.claude-plugin/plugin.json +12 -0
- package/plugin/.mcp.json +10 -0
- package/plugin/README.md +44 -0
- package/plugin/bin/fanout +48 -0
- package/plugin/commands/crew.md +11 -0
- package/plugin/commands/fanout.md +30 -0
- package/plugin/commands/watch.md +20 -0
- package/plugin/hooks/hooks.json +28 -0
- package/plugin/skills/fanout/SKILL.md +126 -0
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
---
|
|
2
|
+
description: Watch a running mission and review each run as it finishes
|
|
3
|
+
argument-hint: "[mission id]"
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
Watch the mission **$ARGUMENTS** (if no id is given, use the most recent one you launched).
|
|
7
|
+
|
|
8
|
+
Subscribe to the live feed rather than polling in a loop: start a Monitor on the daemon's WebSocket, which only
|
|
9
|
+
sends the events a lead acts on.
|
|
10
|
+
|
|
11
|
+
```
|
|
12
|
+
ws://127.0.0.1:<port>/events?for=lead&missionId=$ARGUMENTS&token=<token>
|
|
13
|
+
```
|
|
14
|
+
|
|
15
|
+
The port is in `~/.fanout/daemon.json` and the token in `~/.fanout/token`. Read both; never print the token.
|
|
16
|
+
|
|
17
|
+
When a run finishes, review it straight away with `run_diff` while the rest are still going: read what it changed,
|
|
18
|
+
look first at anything written outside its declared scope, and tell the user in two or three lines what you would
|
|
19
|
+
keep and what you would not. When every run has finished, give the mission summary: what succeeded, what failed and
|
|
20
|
+
why, and what you recommend merging.
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
{
|
|
2
|
+
"hooks": {
|
|
3
|
+
"SessionStart": [
|
|
4
|
+
{
|
|
5
|
+
"hooks": [
|
|
6
|
+
{
|
|
7
|
+
"type": "command",
|
|
8
|
+
"command": "node",
|
|
9
|
+
"args": ["${CLAUDE_PLUGIN_ROOT}/bin/fanout", "status"],
|
|
10
|
+
"timeout": 20
|
|
11
|
+
}
|
|
12
|
+
]
|
|
13
|
+
}
|
|
14
|
+
],
|
|
15
|
+
"Stop": [
|
|
16
|
+
{
|
|
17
|
+
"hooks": [
|
|
18
|
+
{
|
|
19
|
+
"type": "command",
|
|
20
|
+
"command": "node",
|
|
21
|
+
"args": ["${CLAUDE_PLUGIN_ROOT}/bin/fanout", "owed"],
|
|
22
|
+
"timeout": 20
|
|
23
|
+
}
|
|
24
|
+
]
|
|
25
|
+
}
|
|
26
|
+
]
|
|
27
|
+
}
|
|
28
|
+
}
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: fanout
|
|
3
|
+
description: Lead a crew of agent CLIs (Codex, Grok, Claude) through the Fanout tools - plan a mission, fan it out into isolated git worktrees, watch it, and review every diff before anything merges. Use when a task splits into independent pieces that can run in parallel, or when the user asks for the crew, a fan-out, or a mission. Not for a single edit you can make yourself.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Leading a crew with Fanout
|
|
7
|
+
|
|
8
|
+
The Fanout MCP server runs the other agent CLIs on this machine. You stay the lead: you plan, you review, and the
|
|
9
|
+
user decides what merges. The tools do the mechanics — worktrees, launching, limits, the ledger — so that your
|
|
10
|
+
judgment is the only thing that has to be good.
|
|
11
|
+
|
|
12
|
+
## Before you say anything is done
|
|
13
|
+
|
|
14
|
+
This part applies to **your own** code, not only to work you fanned out. Most of the code in a session is written
|
|
15
|
+
by you and read by nobody else, and your own reasoning is exactly what makes your mistakes invisible to you: you
|
|
16
|
+
know why it is right, so it looks right.
|
|
17
|
+
|
|
18
|
+
So before telling the user work is finished, call `check_claims` with two to four things you believe about your own
|
|
19
|
+
uncommitted changes. Another vendor's CLI reads them cold — no plan, no justification, just the diff — and tries to
|
|
20
|
+
falsify each one.
|
|
21
|
+
|
|
22
|
+
**Write claims that can be proven false.**
|
|
23
|
+
|
|
24
|
+
| Write this | Not this |
|
|
25
|
+
|---|---|
|
|
26
|
+
| "No caller of `total()` passes fewer than two arguments" | "The refactor is safe" |
|
|
27
|
+
| "Nothing outside `src/api/` changed behaviour" | "It works" |
|
|
28
|
+
| "Every new branch in `parse()` has a test" | "Well tested" |
|
|
29
|
+
| "A symlink cannot lead the reviewer outside the copy" | "Isolation is handled" |
|
|
30
|
+
|
|
31
|
+
Half the value arrives before the tool runs: a claim you cannot phrase falsifiably is usually one you have not
|
|
32
|
+
actually checked.
|
|
33
|
+
|
|
34
|
+
**Read the verdicts as written.** `confirmed` means it was actively checked. `unclear` means the reader could not
|
|
35
|
+
tell — which is *not* a pass, and is worth a second look at whether the claim was answerable. `refuted` means stop:
|
|
36
|
+
fix it, and when you fix it, add the test that would have caught it, so it cannot come back.
|
|
37
|
+
|
|
38
|
+
State the refutations to the user in the reader's own words. A second opinion that you summarise into agreement is
|
|
39
|
+
not a second opinion.
|
|
40
|
+
|
|
41
|
+
## When this is worth it
|
|
42
|
+
|
|
43
|
+
Fan out when the work splits into pieces that touch **different files** and can be described precisely. Two lines
|
|
44
|
+
that need the same file are one line, or two lines in sequence. A single edit you can make in a minute is not a
|
|
45
|
+
mission; making it yourself is faster and better.
|
|
46
|
+
|
|
47
|
+
Good shapes:
|
|
48
|
+
|
|
49
|
+
| Shape | Seat | Scope |
|
|
50
|
+
|---|---|---|
|
|
51
|
+
| Map a system, find bugs, write a spec | auditor (read-only) | no write scope |
|
|
52
|
+
| Implement a well-specified change with tests | builder | the files it owns |
|
|
53
|
+
| Write tests for a rule before it exists | tester | the test files |
|
|
54
|
+
| One server contract, several clients | builders in parallel | one area each |
|
|
55
|
+
|
|
56
|
+
## The loop
|
|
57
|
+
|
|
58
|
+
1. `repo_overview` and `seats` before planning. No ready seat, no mission.
|
|
59
|
+
2. Write the plan. Per line: a narrow write scope, a prompt that names files, an example, the project's check
|
|
60
|
+
commands and "do not commit", and the seat that suits the work. Risky or subtle work goes to the strongest seat;
|
|
61
|
+
mechanical work to the cheapest. Claude is opt-in, because the lead already spends that subscription.
|
|
62
|
+
3. `plan_check`. It refuses overlapping scopes, missing seats, dangerous flags and uncommitted work inside a scope.
|
|
63
|
+
Fix the plan rather than arguing with the gate.
|
|
64
|
+
4. `launch`. Tell the user the mission id and what each line will do.
|
|
65
|
+
5. `mission_status` while it runs; review each run with `run_diff` as it finishes rather than all at the end.
|
|
66
|
+
6. Report per run: what changed, what you would keep, what you would not, what you could not verify. The user
|
|
67
|
+
decides what merges.
|
|
68
|
+
|
|
69
|
+
## Writing a prompt an agent can actually follow
|
|
70
|
+
|
|
71
|
+
Name the files. Give one example of input and expected output. State the invariants it must not break. Give the
|
|
72
|
+
exact check commands. Say "do not commit, do not create branches". Ask for a final message that lists what changed,
|
|
73
|
+
what it deliberately left alone, and the test counts — and say plainly when a sandbox could not run a check.
|
|
74
|
+
|
|
75
|
+
Agents do better with a checklist than with a goal.
|
|
76
|
+
|
|
77
|
+
## Reviewing what comes back
|
|
78
|
+
|
|
79
|
+
- Read the diff, not the report. `run_diff` reads the workspace itself; the report is the agent's own account.
|
|
80
|
+
- Look first at anything written **outside its declared scope**. That is where the surprises are.
|
|
81
|
+
- Check the invariants yourself: money, auth, migrations, anything that picks a default value, anything that could
|
|
82
|
+
leak a real value into a test.
|
|
83
|
+
- A bug fix needs a test that fails on the old code. If it does not have one, that is the rework.
|
|
84
|
+
- Never present an agent's "tests pass" as your own verification. Run the project's checks yourself after applying.
|
|
85
|
+
|
|
86
|
+
## Bringing a run home
|
|
87
|
+
|
|
88
|
+
When an agent finishes, the gate is four tools in order, and each one records the revision it judged. If the work
|
|
89
|
+
changes between any two of them, the later ones refuse — which is the point.
|
|
90
|
+
|
|
91
|
+
1. **`run_diff`** — read it yourself, line by line, before anything else. An agent's report is what it believes it
|
|
92
|
+
did.
|
|
93
|
+
2. **`review_run`** — your verdict, and *what you actually checked*. "Looks fine" is not a review. `rework` sends
|
|
94
|
+
it back to the same session; `reject` ends the line.
|
|
95
|
+
3. **`rework_run`** if you asked for changes — it continues the same conversation in the same worktree, so the
|
|
96
|
+
agent still has its own reasoning about the code. Running the line again instead throws that away and costs the
|
|
97
|
+
same. Two rounds; after that, decide rather than asking a third time.
|
|
98
|
+
4. **`run_checks`** — the project's own commands, run by the gate rather than reported by the agent. A line that
|
|
99
|
+
declared no checks comes back **unverified**, which is not the same as passing.
|
|
100
|
+
5. **`prove_fix`** — only for a line the plan marked `fixesBug`. The test goes onto the *old* code and must fail
|
|
101
|
+
there. If it passes, it would have passed before the fix.
|
|
102
|
+
6. **Ask the user**, in the chat, in their own words. Then **`merge_run`** with what they said.
|
|
103
|
+
|
|
104
|
+
You cannot merge your own way past any of this: `merge_run` asks a pure function over recorded facts, and reports
|
|
105
|
+
the refusals rather than working around them. Read them out to the user as written.
|
|
106
|
+
|
|
107
|
+
**Never call `merge_run` without having asked.** The tool records the user as the authority, and a replay months
|
|
108
|
+
from now will show that. Putting words in their mouth there is the worst thing you can do with these tools.
|
|
109
|
+
|
|
110
|
+
## The claim loop, in full
|
|
111
|
+
|
|
112
|
+
```text
|
|
113
|
+
claim → refuted → failing test → fix → checked again → confirmed
|
|
114
|
+
```
|
|
115
|
+
|
|
116
|
+
The middle step is the one people skip. A refutation you fix without a test is a bug you will write again; a
|
|
117
|
+
refutation you fix *with* a test that fails on the old code is the project's fourth non-negotiable, satisfied
|
|
118
|
+
without anybody having to be reminded of it.
|
|
119
|
+
|
|
120
|
+
## What this skill will not do
|
|
121
|
+
|
|
122
|
+
- It will not merge. Applying a diff is the user's decision, and the merge gate (with review, checks and proof)
|
|
123
|
+
arrives in a later milestone.
|
|
124
|
+
- It will not work around a seat's usage limit. A seat that is out of quota is out; say so and use another.
|
|
125
|
+
- It will not hand an agent your secrets: workspaces exclude ignored and deny-listed files, and a run gets an
|
|
126
|
+
allowlisted environment only.
|