feat(brainstorm): swarm-simulated discovery replacing the serial interview

Replace brainstorm's ~10 serial user round-trips with a parallel
populate-then-triage: enumerate the load-bearing forks, populate them with a
grounded synthetic-user swarm (mandatory per-answer citation), and triage — a
fork the swarm settles on a cited shared ground is decided (user vetoes), a
split or ungrounded-consensus is a direction fork the user settles. A
cross-check surfaces any fork the orchestrator's own enumeration held open but
the swarm closed. A fire-check + grounding floor skip the swarm when it would
be ceremony.

Under /boss the swarm runs autonomously: convergent forks are decided and
recorded on the reference issue, only a divergent direction fork (or a
sub-floor greenfield design) bounces. Retires trigger-4's "fresh brainstorm is
too high-context to run autonomously" rationale — the swarm is the compaction.

- brainstorm/agents/synthetic-user.md: new read-only swarm agent
- brainstorm/SKILL.md: full rewrite to the swarm flow + new Iron Law
- boss/SKILL.md: autonomous swarm-brainstorm (Iron Law, trigger 4, asymmetry,
  notifications, rationalisations, red flag)
- docs/pipeline.md: brainstorm phase description
- specify/SKILL.md: brainstorm characterised as swarm discovery, not interview

closes #19
This commit is contained in:
2026-06-30 22:59:25 +02:00
parent dfb53ad7ed
commit c39a817982
5 changed files with 472 additions and 164 deletions
+51 -36
View File
@@ -56,7 +56,9 @@ re-enters by typing `/boss` again.
NO AUTONOMOUS DISPATCH OUTSIDE A `/boss` SESSION. NO AUTONOMOUS DISPATCH OUTSIDE A `/boss` SESSION.
DONE-STATE = QUEUE EMPTY, NOT SUB-GOAL COMPLETE. DONE-STATE = QUEUE EMPTY, NOT SUB-GOAL COMPLETE.
BOUNCE-BACK ONLY ON THE FOUR NAMED TRIGGERS. BOUNCE-BACK ONLY ON THE FOUR NAMED TRIGGERS.
A NEW CYCLE NEVER STARTS AUTONOMOUSLY — IT IS A BOUNCE-BACK. A NEW CYCLE'S DESIGN RUNS AUTONOMOUSLY VIA THE `brainstorm` SWARM — IT DECIDES
THE CONVERGENT (CITED-GROUND) FORKS AND BOUNCES ONLY A DIVERGENT DIRECTION
FORK OR A GREENFIELD DESIGN BELOW THE SWARM'S GROUNDING FLOOR.
``` ```
Universal rules (only-orchestrator-commits, main-is-sacrosanct, Universal rules (only-orchestrator-commits, main-is-sacrosanct,
@@ -144,10 +146,12 @@ route(task):
autonomously, as a bug issue already is. autonomously, as a bug issue already is.
- **Forces a genuine design choice → `brainstorm`.** Writing the work - **Forces a genuine design choice → `brainstorm`.** Writing the work
down would force a choice between two or three plausible designs with down would force a choice between two or three plausible designs with
real trade-offs. Discovery must resolve it first. Starting a fresh real trade-offs. Discovery must resolve it first — and `brainstorm` now
`brainstorm` cycle is itself a bounce-back per §"Direction freedom" **dispatches autonomously**: its synthetic-user swarm decides the forks it
trigger 4 — green-light the cycle (and the session shape) with the can settle on a cited shared ground (recorded on the reference issue) and
user first. bounces only a genuine divergent direction fork, or a greenfield design
below its grounding floor, per §"Direction freedom" trigger 4. A fresh
`brainstorm` is no longer a blanket pre-dispatch bounce.
- **A type/signature edit at a definition site, propagating mechanically - **A type/signature edit at a definition site, propagating mechanically
`compiler-driven`.** The positive trigger is *syntactic and `compiler-driven`.** The positive trigger is *syntactic and
observable*: a carrier/newtype narrowing, a constructor or field observable*: a carrier/newtype narrowing, a constructor or field
@@ -187,13 +191,17 @@ whose handling is a new code path with new observable output — is
which side a change falls on, that doubt is itself the signal it carries which side a change falls on, that doubt is itself the signal it carries
behaviour: route up to tdd/spec, not down to compiler-driven. behaviour: route up to tdd/spec, not down to compiler-driven.
The asymmetry in autonomy — `debug`, `compiler-driven`, `tdd`, and Every entry path now dispatches autonomously — `debug`, `compiler-driven`,
`specify` all dispatch autonomously, while a fresh `brainstorm` cycle `tdd`, `specify`, and `brainstorm` — and what differs is only *what each
bounces back — is **not** a ranking of the paths. It is a consequence of bounces on*, not whether it runs. The old asymmetry (a fresh `brainstorm`
context budget: the four are bounded (no open Q&A; `compiler-driven` and bouncing before it starts) rested on context budget: a serial-interview
`debug` self-settle on a run), whereas a fresh `brainstorm` is `brainstorm` was high-context discovery the orchestrator could not compact on
high-context discovery the orchestrator cannot compact on its own (see its own. The swarm retires that rationale — it IS the compaction: the
trigger 4). `specify` dispatched in `/boss` signs through its own Step-6 orchestrator gets back a triaged populated space, not a 10-round interview
transcript, so `brainstorm` decides the forks the swarm settles on a cited
ground and bounces only a divergent direction fork (or a greenfield design
below its grounding floor — see trigger 4). `specify` dispatched in `/boss`
signs through its own Step-6
gate — the Step-5 `grounding-check` `PASS`, an independent agent's gate — the Step-5 `grounding-check` `PASS`, an independent agent's
verdict against currently-green tests, not the orchestrator's confidence; verdict against currently-green tests, not the orchestrator's confidence;
the run then continues to `planner` without pausing. A no-override the run then continues to `planner` without pausing. A no-override
@@ -220,8 +228,10 @@ All entry paths are always available — none is profile-gated. The
cascade is the order of decision: the lighter arms (`debug`, cascade is the order of decision: the lighter arms (`debug`,
`compiler-driven`, `tdd`) carry positive triggers and dispatch `compiler-driven`, `tdd`) carry positive triggers and dispatch
autonomously, `specify` dispatches autonomously and pauses at its autonomously, `specify` dispatches autonomously and pauses at its
sign-off gate, and a fresh `brainstorm` is the one path that bounces sign-off gate, and `brainstorm` dispatches its swarm autonomously —
back to the user before it starts. deciding the forks it can settle on a cited ground and bouncing only a
divergent direction fork (or a greenfield design below its grounding
floor).
If the working tree is mid-flight (uncommitted changes left over If the working tree is mid-flight (uncommitted changes left over
from a previous session): inspect first, then resume the right from a previous session): inspect first, then resume the right
@@ -373,24 +383,28 @@ Bounce back to the user only when:
project's direction (a fundamental design flaw, an external project's direction (a fundamental design flaw, an external
dependency failure, a discovered invariant violation). dependency failure, a discovered invariant violation).
- The user has explicitly asked for a checkpoint. - The user has explicitly asked for a checkpoint.
- **The next item on the queue is a new cycle** — i.e. a top- - **The `brainstorm` swarm surfaces a divergent direction fork.** A new
level work container (a milestone) that has no spec file yet and cycle's design runs autonomously through the `brainstorm` swarm, which
would require dispatching `brainstorm` to even begin. decides the forks it can settle on a cited shared ground and records them on
Continuing an open cycle (next iteration, audit, fieldtest, the reference issue. What bounces is the residue: a fork the swarm splits on,
post-audit tidy) is autonomous; *starting* a new cycle is a or agrees on with no citable ground (ungrounded-consensus), or one the
bounce-back. orchestrator's own Step-2 enumeration held open — a genuine **direction
fork** only the user's preference can settle. A greenfield design *below the
swarm's grounding floor* (no ledger to cite against) likewise bounces,
because the swarm cannot run honestly and the work needs a human interview.
Continuing an open cycle and *starting* a new one are now both autonomous up
to this residue.
**Why this is different from the other three triggers.** **Why this is different from the other three triggers.**
Cross-cycle work is high-context work. A fresh brainstorm This is the design-judgement checkpoint the swarm cannot discharge. The
alone routinely consumes tens of thousands of tokens on swarm compacts the discovery — the orchestrator gets back a triaged
grounding-check reads, design Q&A, and spec drafting — on top populated space, not a high-context interview transcript — so the old "a
of whatever context the just-closed cycle left behind. The fresh brainstorm is too high-context to run autonomously" rationale is
orchestrator cannot compact its own context window; only the retired (the swarm IS the compaction). What stays genuinely the user's is
user can decide that the right shape for the next cycle is a the direction fork itself: a choice no source settles, where a guessed
fresh session rather than a continuation. A new cycle is default is the reactive-overreach the discipline forbids. Surface it as a
therefore the natural checkpoint: stop, surface the vetoable problem-state notify naming, in the user's terms, the design choice
candidate, let the user pick the session shape (continue here that needs them; the convergent decisions ride along on the reference issue.
/ spawn fresh / defer / pick a different backlog item).
A summary of what shipped is fine and welcome — but in A summary of what shipped is fine and welcome — but in
autonomous mode, follow it with the next dispatch, not a autonomous mode, follow it with the next dispatch, not a
@@ -416,8 +430,9 @@ narrow one for spec auto-sign:
freedom" — design fork the orchestrator cannot resolve, an freedom" — design fork the orchestrator cannot resolve, an
unexpected invariant violation, an external dependency unexpected invariant violation, an external dependency
failure, the user has explicitly asked for a checkpoint, or failure, the user has explicitly asked for a checkpoint, or
the next backlog item is a new cycle (no spec yet) and the `brainstorm` swarm surfaced a divergent direction fork
starting it would force a fresh `brainstorm`. (or a greenfield design below its grounding floor) that needs
the user's call.
3. **Auto-sign.** The 3. **Auto-sign.** The
orchestrator signed a spec in the user's place and is orchestrator signed a spec in the user's place and is
@@ -667,13 +682,13 @@ the user wants it — there is no autonomous filing to govern.
| "Top of the backlog has two equally good options, I'll just pick one" | If both are substantive and the choice is non-obvious, that's a real fork — bounce back. The cost of a wrong pick (working-tree discard) is higher than the cost of one short ping to the user. | | "Top of the backlog has two equally good options, I'll just pick one" | If both are substantive and the choice is non-obvious, that's a real fork — bounce back. The cost of a wrong pick (working-tree discard) is higher than the cost of one short ping to the user. |
| "User said 'until X then notify', X just completed, notify now" | Check whether X was actually the last actionable thing. If hitting X leaves an open cycle with obvious follow-up, the user's intent was "wake me when there's nothing else to do" — continue. | | "User said 'until X then notify', X just completed, notify now" | Check whether X was actually the last actionable thing. If hitting X leaves an open cycle with obvious follow-up, the user's intent was "wake me when there's nothing else to do" — continue. |
| "Notify can name the iteration code — user will figure out what it means" | No. The notify text is for the user-as-reader who did not watch the orchestrator work. Iteration codes, crate names, function identifiers, type names — all internal, all banned. | | "Notify can name the iteration code — user will figure out what it means" | No. The notify text is for the user-as-reader who did not watch the orchestrator work. Iteration codes, crate names, function identifiers, type names — all internal, all banned. |
| "The previous cycle closed cleanly and the next backlog item is obvious — just dispatch `brainstorm` and keep going" | No. Starting a new cycle is itself a bounce-back. A fresh `brainstorm` is high-context work, and the orchestrator cannot compact its own context — only the user can decide whether the next cycle wants a fresh session or a continuation of this one. The "obviousness" of the candidate is irrelevant; the *cross-cycle hop* is the checkpoint, not the topic choice. | | "The previous cycle closed cleanly and the next backlog item is obvious — just dispatch `brainstorm` and keep going" | Dispatching `brainstorm` IS now the autonomous move — its swarm decides the forks it can settle on a cited ground and records them. What you may not do is auto-decide a *divergent direction fork* the swarm could not ground; that bounces. Dispatch the swarm, decide the convergent forks, bounce only the residue. |
| "It's the same broad area as the cycle I just closed, that's not really a new cycle" | If there is no spec file for it yet and it would route through `brainstorm` to get one, it IS a new cycle for this rule's purposes. The rule keys on "needs a fresh spec", not on subjective continuity. | | "The swarm all converged, so I can auto-decide the whole design and move on" | Only forks converged on a *cited shared ground* are decided. Same-model stances agreeing with no citable ground is ungrounded-consensus — a direction fork that bounces, not a decision. Auto-deciding bare agreement is the false-convergence trap that ships the user's once-per-project fork past them. |
| "Feature work, so route it to `brainstorm` — that's the safe default" | The entry paths are an ordered cascade, none the default. Routing a settled design to `brainstorm` re-litigates decided choices; routing a test-specifiable item there wastes the test path; routing a behaviour-preserving type-edit there is the heavy-path gravity well this whole reflection exists to break. Walk the cascade and take the first matching positive trigger. The only tilt toward `brainstorm` is a genuinely unresolved fork — and that is a fork, not a default. | | "Feature work, so route it to `brainstorm` — that's the safe default" | The entry paths are an ordered cascade, none the default. Routing a settled design to `brainstorm` re-litigates decided choices; routing a test-specifiable item there wastes the test path; routing a behaviour-preserving type-edit there is the heavy-path gravity well this whole reflection exists to break. Walk the cascade and take the first matching positive trigger. The only tilt toward `brainstorm` is a genuinely unresolved fork — and that is a fork, not a default. |
| "It's just a mechanical rename across N files — run the full implement loop on it" | That is the `compiler-driven` arm's job, not the heavy loop. Route it there; the type checker enumerates the sites, and the done-signal (clean build AND suite green unchanged) is the gate. Funnelling a behaviour-preserving edit through the full per-task loop is the disproportionality the cascade was added to fix. | | "It's just a mechanical rename across N files — run the full implement loop on it" | That is the `compiler-driven` arm's job, not the heavy loop. Route it there; the type checker enumerates the sites, and the done-signal (clean build AND suite green unchanged) is the gate. Funnelling a behaviour-preserving edit through the full per-task loop is the disproportionality the cascade was added to fix. |
| "The compiler-driven edit built clean — that's the done-signal, commit" | Clean build is only half. The done-signal is clean build **AND suite green unchanged**. A behaviour change can build clean; the unchanged-green suite is what catches it. No suite run, no commit — and if the suite isn't green-unchanged, bounce to `debug`. | | "The compiler-driven edit built clean — that's the done-signal, commit" | Clean build is only half. The done-signal is clean build **AND suite green unchanged**. A behaviour change can build clean; the unchanged-green suite is what catches it. No suite run, no commit — and if the suite isn't green-unchanged, bounce to `debug`. |
| "It's a bug but the fix is a one-line type edit — route it `compiler-driven`" | No. An observed bug is first in the cascade → `debug`, RED-first, regardless of how mechanical the fix looks. The bug-gate sits before the type-edit arm precisely so a regression cannot launder itself around RED-first. | | "It's a bug but the fix is a one-line type edit — route it `compiler-driven`" | No. An observed bug is first in the cascade → `debug`, RED-first, regardless of how mechanical the fix looks. The bug-gate sits before the type-edit arm precisely so a regression cannot launder itself around RED-first. |
| "The issue is exhaustive but it's a new cycle, so bounce to the user before `specify`" | `specify` direct-entry is bounded and autonomously dispatchable — it is NOT the high-context `brainstorm` cycle that trigger 4 reserves for the user. Dispatch it; it will pause at its own user-review gate for sign-off. The pre-dispatch bounce is for an *open* design that needs discovery, not for a settled one that needs only production. | | "The issue is exhaustive but it's a new cycle, so bounce to the user before `specify`" | `specify` direct-entry is bounded and autonomously dispatchable — a settled design needs production, not discovery; don't route it through `brainstorm` at all. And even an *open* design no longer blanket-bounces: its swarm runs autonomously and bounces only a divergent direction fork. The bounce is for an unresolved *direction*, never for "it's new". |
| "`tdd` is the secondary skill, `brainstorm` is the real entry" | All entry paths are always available. The choice among them is the cascade, walked per item — not a habit of treating `brainstorm` as primary and the lighter arms as exceptions. The lighter arms exist to be reached; reaching past them by elimination is the failure the verification axis was added to prevent. | | "`tdd` is the secondary skill, `brainstorm` is the real entry" | All entry paths are always available. The choice among them is the cascade, walked per item — not a habit of treating `brainstorm` as primary and the lighter arms as exceptions. The lighter arms exist to be reached; reaching past them by elimination is the failure the verification axis was added to prevent. |
| "This spec is clearly good — I'll sign it on my judgement" | Your judgement is not the signature; the Step-5 `grounding-check` `PASS` is. Run grounding and sign on the PASS. A no-override grounding `BLOCK` routes to the human — never signed over on confidence. (The old unanimous `spec-skeptic` panel is retired; do not re-introduce it as a gate.) | | "This spec is clearly good — I'll sign it on my judgement" | Your judgement is not the signature; the Step-5 `grounding-check` `PASS` is. Run grounding and sign on the PASS. A no-override grounding `BLOCK` routes to the human — never signed over on confidence. (The old unanimous `spec-skeptic` panel is retired; do not re-introduce it as a gate.) |
| "There's an open fork — I'll bounce to `brainstorm` to be safe" | If you can *derive* an answer (sources, code, consistency, risk), decide it boldly and record it in the reference issue. Only a *pure-preference* fork bounces. Bouncing a derivable fork is exactly the timidity the bold stance retired; unsure if your leaning is bias, pull one ad-hoc `spec-skeptic` lens, then decide. | | "There's an open fork — I'll bounce to `brainstorm` to be safe" | If you can *derive* an answer (sources, code, consistency, risk), decide it boldly and record it in the reference issue. Only a *pure-preference* fork bounces. Bouncing a derivable fork is exactly the timidity the bold stance retired; unsure if your leaning is bias, pull one ad-hoc `spec-skeptic` lens, then decide. |
@@ -692,7 +707,7 @@ the user wants it — there is no autonomous filing to govern.
- About to autonomously dispatch in a session where the user did NOT type `/boss`. - About to autonomously dispatch in a session where the user did NOT type `/boss`.
- About to send a notify that names a crate, an iteration code, or an agent. - About to send a notify that names a crate, an iteration code, or an agent.
- About to bounce back at every iteration boundary "just to be safe" — that's reactive deference, not direction freedom. - About to bounce back at every iteration boundary "just to be safe" — that's reactive deference, not direction freedom.
- About to dispatch `brainstorm` on a backlog issue that does not yet have a spec file, without first bouncing back to the user. New cycles never start autonomously. - About to *auto-decide* a divergent direction fork the `brainstorm` swarm could not ground (or could only agree on with no citable ground) instead of bouncing it — or, conversely, bouncing the whole fresh `brainstorm` "to be safe" instead of running its swarm autonomously and bouncing only the divergent residue.
- About to route feature work to `brainstorm` without walking the Entry-path cascade — defaulting to it because it "feels safer" than the lighter arms, rather than taking the first matching positive trigger. Routing a *settled* design, a *test-specifiable* item, or a *behaviour-preserving type-edit* to `brainstorm` is as much a failure as skipping discovery on an open one. - About to route feature work to `brainstorm` without walking the Entry-path cascade — defaulting to it because it "feels safer" than the lighter arms, rather than taking the first matching positive trigger. Routing a *settled* design, a *test-specifiable* item, or a *behaviour-preserving type-edit* to `brainstorm` is as much a failure as skipping discovery on an open one.
- About to route an observed bug to the `compiler-driven` arm because "the fix is mechanical" — a regression is `debug`, RED-first; the bug-gate is first in the cascade for exactly this reason. - About to route an observed bug to the `compiler-driven` arm because "the fix is mechanical" — a regression is `debug`, RED-first; the bug-gate is first in the cascade for exactly this reason.
- About to route a behaviour-encoding change to `compiler-driven` because it "looks mechanical" — apply the straddle rule: if the change encodes new behaviour it is `tdd` / `spec-driven`, and doubt means it carries behaviour. - About to route a behaviour-encoding change to `compiler-driven` because it "looks mechanical" — apply the straddle rule: if the change encodes new behaviour it is `tdd` / `spec-driven`, and doubt means it carries behaviour.
+270 -122
View File
@@ -1,45 +1,55 @@
--- ---
name: brainstorm name: brainstorm
description: Use when a new cycle is starting and the design is NOT yet settled — gathers requirements, explores 2-3 approaches with trade-offs, presents a sectioned design with user approval, then hands the ratified design to the specify skill to produce the spec. The optional discovery front-end; when the design is already settled in the sources, skip to specify directly. Applies even when the user says they have a clear vision. description: Use when a new cycle is starting and the design is NOT yet settled — enumerates the load-bearing design forks, populates them with a parallel swarm of grounded synthetic-user stances instead of a serial interview, triages the result (forks the swarm settles on a cited ground are decided; forks it splits on are the user's call), then hands the ratified design to specify. The optional discovery front-end; when the design is already settled in the sources, skip to specify directly. Applies even when the user says they have a clear vision.
--- ---
# brainstorm — cycle spec generator # brainstorm — cycle discovery front-end
> **Violating the letter of these rules is violating the spirit.** > **Violating the letter of these rules is violating the spirit.**
## Overview ## Overview
Discovery is where the orchestrator does the *deciding* work — Discovery is where the orchestrator does the *deciding* work — surfacing the
surfacing requirements, exploring approaches, and ratifying a design load-bearing forks a new cycle forces, resolving the ones it can ground an
with the user. It is the front-end that resolves a genuine design fork answer for, and putting the rest to the user. It is the front-end that
before any spec is written. Skipping it when the design is genuinely settles a genuine design fork before any spec is written. Skipping it when the
open means shipping the user's intuition unfiltered, which is exactly design is genuinely open means shipping the user's intuition unfiltered, which
the reactive-deference failure mode the orchestrator discipline exists is exactly the reactive-deference failure the orchestrator discipline exists
to prevent. to prevent.
What `brainstorm` no longer does is run a **serial interview** — one question
per message, a per-section ratification gate — to get there. That ceremony
spent ~10 blocking round-trips per cycle to catch a divergence from the
orchestrator's recommendation that, across a whole project, materialises about
once. Instead `brainstorm` **populates the design space in parallel**: it
enumerates the forks, dispatches a swarm of grounded, genuinely-opposed
synthetic-user stances to answer them, and triages the result. Where the
stances converge on a *cited* common ground the fork was derivable — it is
decided, and the user only vetoes. Where they genuinely split, no source
settles it — it is a **direction fork**, and that is the user's call. Direction
is never delegated downstream; it is set here, by the user, on exactly the
forks that turn out to be theirs.
`brainstorm` does not write the spec. Its terminal state is handing the `brainstorm` does not write the spec. Its terminal state is handing the
ratified design to `specify` (the spec-production core), which applies ratified design to `specify` (the spec-production core), which applies the
the acceptance criterion, writes the spec under `docs/specs`, runs acceptance criterion, writes the spec under `docs/specs`, runs the gates, and
the gates, and takes user sign-off. When the design is *already* takes sign-off. When the design is *already* settled in the sources,
settled in the sources, `brainstorm` is skipped entirely and the work `brainstorm` is skipped entirely and the work enters through `specify`.
enters through `specify` directly.
## When to Use / Skipping ## When to Use / Skipping
Triggers: Triggers:
- A new cycle is starting (e.g. user proposes a new feature - A new cycle is starting (a new feature area, a new subsystem, or a major
area, a new subsystem, or a major refactor of an existing refactor of an existing one) whose design is genuinely open.
one). - A cycle-scope spec is missing for an existing line of work and one is needed
- A cycle-scope spec is missing for an existing line of retroactively, and the design behind it was never settled.
work and one is needed retroactively.
**Skip `brainstorm` (enter through the named alternative) for:** **Skip `brainstorm` (enter through the named alternative) for:**
- A design already settled in the sources — an exhaustive issue, a - A design already settled in the sources — an exhaustive issue, a long
long in-context discussion, settled design docs. Use `specify` in-context discussion, settled design docs. Use `specify` directly:
directly: discovery would only re-litigate decisions the sources discovery would only re-litigate decisions the sources already made.
already made.
- A test-specifiable feature — use `tdd` directly. - A test-specifiable feature — use `tdd` directly.
- A bug-fix iteration — use `debug` directly. - A bug-fix iteration — use `debug` directly.
- A tidy iteration — use `audit` directly. - A tidy iteration — use `audit` directly.
@@ -47,156 +57,294 @@ Triggers:
**Do not skip `brainstorm`** when the design is genuinely open: **Do not skip `brainstorm`** when the design is genuinely open:
- A user request framed as "I have a clear vision, just plan it" whose - A request framed as "I have a clear vision, just plan it" whose vision still
vision still hides an unresolved fork. hides an unresolved fork.
- A cycle where a load-bearing decision is not yet made. - A cycle where a load-bearing decision is not yet made.
The discriminator is the design line: if the sources resolve every The discriminator is the design line: if the sources resolve every
load-bearing decision, the work belongs to `specify`; if writing the load-bearing decision, the work belongs to `specify`; if writing the spec
spec would force you to *pick* one, discovery is what resolves it, and would force you to *pick* one, discovery is what resolves it, and that is
that is `brainstorm`. `brainstorm`.
## The Iron Law
```
ENUMERATE EVERY LOAD-BEARING DESIGN FORK BEFORE POPULATING ANYTHING — THIS
ENUMERATION IS ALSO THE ORCHESTRATOR'S OWN INDEPENDENT SIGNAL, USED LATER TO
CROSS-CHECK THE SWARM.
A FORK THE SWARM SETTLES ON A *CITED SHARED GROUND* WAS DERIVABLE -> PRESENT IT
DECIDED (USER VETOES), AND RECORD THE GROUND. A FORK THE SWARM SPLITS ON, OR
AGREES ON WITH *NO CITABLE GROUND* (UNGROUNDED-CONSENSUS), IS A DIRECTION
FORK -> THE USER'S CALL. THE LINE IS GROUNDED-DERIVABILITY VS PREFERENCE,
NOT SMALL VS LARGE, AND NOT BARE AGREEMENT.
A FORK THE ORCHESTRATOR'S OWN ENUMERATION FLAGGED OPEN BUT THE SWARM CLOSED IS
SURFACED TO THE USER ANYWAY — THE SWARM NEVER ERASES A FORK THE ORCHESTRATOR
INDEPENDENTLY HELD OPEN.
THE DECIDING WORK IS NEVER SKIPPED. A DESIGN PRESENTED WITHOUT THE FORK
ENUMERATION + SWARM + TRIAGE DONE IS THE RUBBER-STAMP BETRAYAL, NOT DISCOVERY.
DESIGN DIRECTION IS SET HERE BY THE USER — NEVER DELEGATED TO THE SWARM, NEVER
TO `specify`.
```
Every clause is non-negotiable. The swarm is *evidence*, not an oracle: it
populates the space and exposes where stances split, but the convergent-vs-
direction verdict is the orchestrator's derivability judgement (the same one
`specify` Step 1.5 applies), and bare agreement among same-model stances is
never that judgement — only agreement on a citable ground is.
## The Process ## The Process
### Step 1 — Explore project context ### Step 1 — Explore project context
Before asking any clarifying questions: Before enumerating anything:
- `git log -5 --format=full` for the full bodies of the most - `git log -5 --format=full` for the full bodies of the most recent iter /
recent iter / audit commits — current state of the project. audit commits — current state of the project.
- If the project has a design ledger (its CLAUDE.md project facts name - If the project has a design ledger (its CLAUDE.md project facts name it),
it), walk to the relevant contracts for the invariants the new cycle walk to the relevant contracts for the invariants the new cycle might touch.
might touch. - When reading any file under the project's design models, note its `status` /
- When reading any file under the project's design models, if it has `validated-against` frontmatter if present: `status: aspirational` means its
them, or the ledger's "model" rows, note its `status` / code is a target, not verified fact. Track which content is flagged for
`validated-against` frontmatter if present: `status: lift-time validation when `specify` writes the spec.
aspirational` means its code is a target, not verified fact.
Track which content you may lift from such a source — it is
flagged for lift-time validation when `specify` writes the spec.
- `git log --oneline -20` for the chronological scan. - `git log --oneline -20` for the chronological scan.
- Identify scope: is this one cycle, or does it need to be - Identify scope: is this one cycle, or does it need to be decomposed into
decomposed into sub-cycles first? If multi-subsystem, sub-cycles first? If multi-subsystem, decompose.
decompose.
### Step 2 — Ask clarifying questions, one at a time ### Step 2 — Enumerate the load-bearing forks
Multiple-choice when possible (easier to answer). One List the **load-bearing design forks** the cycle forces — the choices that,
question per message — no batching. Focus on: decided differently, would change what ships — exactly as the clarifying
questions you would otherwise have put to the user. Cover at least:
- **Purpose:** what problem does this solve? - **Purpose:** what problem does this solve?
- **Constraints:** what semantic / performance / - **Constraints:** what semantic / performance / compatibility invariants must
compatibility invariants must hold? hold?
- **Success criteria:** how do we know it shipped? - **Success criteria:** how do we know it shipped?
- **Scope:** what is OUT of scope? - **Scope:** what is OUT of scope?
### Step 3 — Propose 2-3 approaches with trade-offs For each fork, privately note whether *you* think it is derivable or genuinely
open. This enumeration is the swarm's input **and** your own independent
signal: a fork you flagged open that the swarm later closes is surfaced to the
user anyway (the Iron Law cross-check). Do not interview the user here — no
serial questions.
Lead with your recommended option and explain why. Each ### Step 2.5 — Fire-check (skip the swarm when it would be ceremony)
approach gets:
- core idea (1-2 sentences) The swarm is justified only when there are **multiple non-trivial forks whose
- **concrete code first, prose second.** The *primary* derivability is genuinely uncertain** *and* there is enough checked-in ground
artefact is the actual program or invocation that should to answer them honestly. Skip it, and resolve inline, when:
work under this approach — written in the project's
canonical authoring or consumer form. Show it. The
implementation shape (changed struct / signature / match-
arm, before → after) is *secondary supporting* detail —
"also useful, not the point" — include it but never let it
stand in for the concrete user-facing code. "The approach
extends the struct with a field" is not an approach; the
user-facing program it makes work (or correctly reject) is.
- substantive trade-offs (semantic fit, schema impact,
performance, composability)
- effort observation (NOT effort as rationale — see the
project's CLAUDE.md on design rationale ≠ implementation
effort)
Wait for user choice before proceeding. - **Too few forks.** Zero or one real fork — answer it directly (a single
derivable fork is decided and noted; a single open one is one question to
the user). Spinning up a swarm for one fork is more machinery than the
ceremony it replaced.
- **Grounding floor not met.** No design ledger, a thin or absent glossary, an
under-specified audience — a greenfield or new-territory project. With
nothing to cite, every synthetic stance confabulates and "convergence" is
100% hallucination wearing a quorum. Below this floor the swarm is NOT
dispatched; fall back to a direct human interview (and under `/boss`, that is
a bounce-back — see § Under `/boss`).
### Step 4 — Present design in sections Record the skip reason in the cycle's notes / the run's reference issue. The
swarm is an optimization for context-rich mature projects, not an
unconditional default.
Scale each section to its complexity (a few sentences if ### Step 3 — Populate the space with the synthetic-user swarm
straightforward, up to 200-300 words if nuanced). Cover:
- Architecture Dispatch the read-only `agents/synthetic-user.md` agent **in parallel, one per
- Components stance, in a single turn** — the same ad-hoc fan-out brainstorm already uses
- Data flow for `plan-recon` and `specify` uses for `spec-skeptic`. No Workflow wrapper: a
- Error handling one-shot stateless fan-out has no re-loop, no ordering, and no in-code verdict
- Testing strategy to enforce, so it is a direct dispatch, not an `implement-loop`-style script.
The design you present here is conceptual — the architecture, The roster is **fixed convention** (no per-project config knob; only the
components, data flow, error handling, and testing strategy the cycle *grounding* — the project's declared audience / ledger / glossary, reached via
commits to. The concrete user-facing code and the before → after standing reading — varies):
implementation shapes are produced downstream, when `specify`
materialises this ratified design into the spec (and applies the
acceptance criterion against that worked code). Your job here is to get
the *design decision* right and ratified, not to write the artefact.
Ask after each section whether it looks right. Be ready to - **minimalist** — convention over config, the smallest change that ships.
revisit earlier sections if a later one surfaces a - **power-user / composability** — capability, extension, what it unlocks.
contradiction. - **maintainer / future-self** — invariants, drift cost, long-term carry.
- **skeptic** — does this need to exist at all (the feature-acceptance
criterion incarnate).
- **off-ledger wildcard** — advocates the direction the project does *not*
imply. Inherently ungrounded by design, so it can only ever surface a fork,
never close one; it exists to keep the swarm from collapsing into
status-quo unanimity.
### Step 5 — Hand off to `specify` Each stance answers the whole `fork_set` with a **mandatory per-answer source
citation or an honest `ungrounded:true`** (the agent's Iron Law). The swarm
ONLY answers the forks; it never authors approaches.
The terminal state of `brainstorm` is invoking `specify`. NO spec file ### Step 4 — Triage and present the populated space
is written here; NO other skill is invoked; NO direct jump to `planner`
or `implement`. This is the **one user stop** in interactive mode. Cluster the stances'
answers per fork and apply the derivability test — the same one `specify`
Step 1.5 uses, measured here against the swarm:
- **Converged on a cited shared ground → DECIDED.** Present it as decided with
the ground shown; the user only vetoes. Record the ground.
- **Split, or converged with no citable ground (ungrounded-consensus) →
DIRECTION FORK.** The user's call. Surface the conflicting positions (and
the wildcard's off-ledger alternative where it raised one) as the things to
weigh. Bare agreement among same-model stances is *not* a decision — demote
it.
- **Cross-check.** Any fork your own Step-2 enumeration flagged open that the
swarm closed is surfaced anyway, never auto-decided.
Then **author the 2-3 approaches** yourself — the orchestrator's job, never the
swarm's. They crystallise out of the populated space: the converged axes are
fixed; each genuine direction fork's conflicting answers *is* an approach the
user weighs. Lead with your recommended option and why; for each:
- **concrete code first, prose second.** The primary artefact is the actual
program or invocation that should work under this approach, in the project's
canonical authoring or consumer form. The implementation shape (changed
struct / signature / match-arm, before → after) is secondary supporting
detail, never a substitute for the user-facing code.
- substantive trade-offs (semantic fit, schema impact, performance,
composability).
- effort observation (NOT effort as rationale — see the project's CLAUDE.md on
design rationale ≠ implementation effort).
Present the conceptual design alongside — Architecture, Components, Data flow,
Error handling, Testing strategy — each scaled to complexity. This design is
conceptual: the concrete user-facing code and the before → after shapes are
materialised downstream when `specify` writes the spec and applies the
acceptance criterion. Your job here is to get the *design decision* right and
ratified, not to write the artefact.
If the populated space shows **every** candidate approach is bad, that is the
"problem is mis-framed" signal — STOP and escalate to the user, do not ratify a
known-bad shape. Three unsatisfying approaches mean the problem is wrong, not
that one must be picked.
### Step 5 — Deepen the forks the user opens
Deepening is **free chat** with the orchestrator by default — the user's
native mode, and the one place they have chosen to engage. A direction fork is
by definition one the swarm could not ground, so re-running the swarm on it
asks the machinery that already failed to converge to try again; do not make a
second swarm round the default. It is an **optional** tool the orchestrator MAY
reach for, scoped to one fork, only to populate *in-direction* sub-options once
the user has tilted toward a direction, or to rescue a fork that turns out to
be mis-framed — `spec-skeptic`-style, a tool reached for, not a gate.
**Capture the resolution.** Whatever the chat settles is folded into the
ratified design narrative handed to `specify`, and minuted on the run's
reference issue (the `specify` Step-1.5 reconciliation-comment / `boss`
decision-log discipline). The free-chat deliberation that used to evaporate now
lands in the pipeline.
### Step 6 — Hand off to `specify`
The terminal state of `brainstorm` is invoking `specify`. NO spec file is
written here; NO other skill is invoked; NO direct jump to `planner` or
`implement`.
Hand off carries the **ratified design narrative**, in-context (same Hand off carries the **ratified design narrative**, in-context (same
orchestrator context — no intermediate artefact): orchestrator context — no intermediate artefact):
- the approach chosen and why - the approach chosen and why
- the constraints and invariants surfaced in Q&A - the constraints and invariants surfaced in the swarm + deepening
- the design sections the user ratified (Step 4) - the design sections the user ratified (Step 4)
- the **decided forks with their cited grounds**, and the **resolved direction
forks with the user's choice** — so `specify`'s chain-entry (Step 1.5,
"re-ground lightly … rather than re-deriving it") reads them as already
settled instead of re-litigating them
- the iteration scope ("the first iteration covers section X+Y") - the iteration scope ("the first iteration covers section X+Y")
`specify` reads this narrative as its source, applies the `specify` reads this narrative as its source, applies the acceptance criterion,
acceptance criterion, writes the spec, runs the parse and writes the spec, runs the parse and grounding-check gates, takes sign-off, and
grounding-check gates, takes user sign-off, and hands off to `planner`. hands off to `planner`. The production gates live there, not here.
The production gates live there, not here.
## Under `/boss` (autonomous)
When the user is away, the swarm runs **autonomously** — the discovery is now
bounded and context-compacting (the orchestrator gets back a triaged populated
space, not a 10-round interview transcript), so a fresh `brainstorm` is no
longer a mandatory pre-dispatch bounce. The autonomous contract mirrors
`specify`'s bold-decide stance:
- **Decide the convergent forks.** A fork the swarm settles on a cited shared
ground is decided autonomously and **recorded on the run's reference issue**
with the ground (the `boss` § Direction-freedom decision-log discipline) —
exactly as `specify` Step 1.5 records a derived fork.
- **Bounce only the divergent direction forks.** A genuine direction fork (split,
or ungrounded-consensus, or one the Step-2 cross-check held open) is the
user's call; there is no user present, so it routes to a **problem-state
bounce** — a vetoable notify naming, in the user's terms, the design choice
that needs them. The convergent decisions ride along; only the genuine forks
stop the loop.
- **Grounding floor → bounce.** If Step 2.5's grounding floor is not met
(greenfield, no ledger), the swarm cannot run honestly and the work needs a
human interview — that remains a bounce-back, on grounding grounds, not on
the retired "fresh brainstorm is too high-context" rationale.
See `../boss/SKILL.md` § Direction freedom (trigger 4) and the Entry-path
reflection for how this folds `brainstorm` into the autonomous cascade.
## Handoff Contract ## Handoff Contract
| Direction | Carrier | | Direction | Carrier |
|-----------|---------| |-----------|---------|
| user → `brainstorm` | new cycle request with a genuinely open design | | user → `brainstorm` | new cycle request with a genuinely open design |
| `brainstorm``specify` (Step 5) | ratified design narrative (approach, constraints, ratified sections, iteration scope) — in-context; no spec file written | | `brainstorm``synthetic-user` swarm (Step 3) | `fork_set` + one `stance` per dispatch + grounding pointers; read-only, parallel, no Workflow |
| `brainstorm` → user / reference issue (Step 4 / `/boss`) | the triaged populated space: decided forks + cited grounds, direction forks surfaced for the user's call |
| `brainstorm``specify` (Step 6) | ratified design narrative (approach, constraints, ratified sections, decided forks + grounds, resolved direction choices, iteration scope) — in-context; no spec file written |
## Common Rationalisations ## Common Rationalisations
| Excuse | Reality | | Excuse | Reality |
|--------|---------| |--------|---------|
| "User says 'clear vision, just plan it' — skip the spec" | "Clear vision" is a starting point, not a spec. The user's intuition hasn't priced in semantic commitments the project carries. Write the spec; frame it as "load-bearing decisions this idea forces on us". | | "User says 'clear vision, just plan it' — skip the discovery" | "Clear vision" is a starting point, not a settled design. Enumerate the forks; the swarm will show which the vision actually resolves and which it papers over. The ones it papers over are the user's to settle. |
| "Cycle is small, two iterations, no spec needed" | Iteration count isn't the metric — feature surface is. A two-iter feature touching design-ledger invariants needs a spec; a CLI flag does not. Assess what the feature changes in invariants. | | "Present my own derived design without the swarm — I already know the answer" | Deriving one answer alone and presenting it polished is the single-guess rubber-stamp. The swarm's diversity is what surfaces the constraint you did not think to derive; the cross-check is what stops your own prior from erasing a fork. Run the swarm (above the fire-check floor) or you are shipping unfiltered intuition with extra steps. |
| "Three approaches in, none feel right, ship the least bad" | Three unsatisfying approaches usually means the problem is mis-framed. Stop, capture the three approaches and what fails about each in the spec's design notes (or escalate to the user), sleep on it. End-of-day pressure is the worst signal to resolve a design fork. | | "The swarm all agreed, so the fork is decided" | Only if they agreed on a *cited shared ground*. Same-model stances agree by shared prior all the time — that is ungrounded-consensus, and it is a direction fork for the user, not a decided one. Bare agreement is the false-convergence trap, not a verdict. |
| "User is busy, present my own design without Q&A" | Reactive deference disguised as decisiveness. The Q&A surfaces constraints the user hasn't articulated; skipping it means shipping the user's defaults, not their intent. | | "There's a direction fork left — re-run the swarm on it to be thorough" | A direction fork is the one the swarm could not ground; re-swarming asks the same non-oracle the same unanswerable question at higher resolution, and the extra detail only makes the guess more persuasive. Deepen it in free chat with the user; a scoped re-swarm is optional and only for in-direction sub-options after the user has tilted. |
| "Spec exists from previous cycle, append to it" | The previous cycle's spec was retired at its close (see `../docs/conventions.md` § Lifecycle) — there is nothing to append to. New cycle = new spec file; the architect reads one cycle's spec at a time, and mixing scopes makes drift review unreadable. | | "Three approaches in, none feel right — ship the least bad" | Three unsatisfying approaches usually means the problem is mis-framed. Stop, capture what fails about each, escalate to the user. End-of-day pressure is the worst signal to resolve a design fork. |
| "Approaches A, B, C are all bad — proceed with A" | This is exactly the moment to surface "the problem is mis-framed" rather than ratify a known-bad shape into the design ledger. Escalate to the user. | | "Spec exists from previous cycle, append to it" | The previous cycle's spec was retired at its close (see `../docs/conventions.md` § Lifecycle) — there is nothing to append to. New cycle = new spec file; mixing scopes makes drift review unreadable. |
| "Let the swarm author the approaches — it has the stances already" | The swarm answers forks; the orchestrator authors approaches. A finished design from the swarm delegates design DIRECTION to a fan-out — the same downstream-delegation sin the reform exists to prevent, just relocated from `specify` to the agents. |
## Red Flags — STOP ## Red Flags — STOP
- "Skip the spec" thoughts (any flavour) - "Skip the discovery" thoughts (any flavour) on a genuinely open design.
- "One paragraph is enough" - Presenting a design without having enumerated the forks, run the swarm
- "User said it's clear, who am I to push back" (above the fire-check floor), and triaged it.
- "The 2-3 approaches all suck, just pick one" - Treating bare swarm agreement as a decision — an ungrounded-consensus
- Inventing a design rationale that's actually about effort, silently auto-decided instead of surfaced as the user's call.
not semantics - A fork your own Step-2 enumeration held open, quietly closed by the swarm and
not surfaced (the cross-check skipped).
- Letting the swarm author the 2-3 approaches, or delegating any design
*direction* to it.
- Re-running the swarm on a direction fork as the default deepening path
instead of free chat with the user.
- Running the swarm below the grounding floor (greenfield, no ledger) and
trusting its confabulated convergence.
- "The 2-3 approaches all suck, just pick one" — that is the mis-framed-problem
escalation, not a forced pick.
- Inventing a design rationale that's actually about effort, not semantics.
## Cross-references ## Cross-references
- **Output target:** `../specify/SKILL.md` — the only valid next - **Agent dispatched:** `agents/synthetic-user.md` — the read-only synthetic
skill. `brainstorm` hands the ratified design to `specify`, which design-stance respondent, dispatched as a parallel swarm in Step 3. A
produces the spec and gates `planner`. There is no direct `spec-skeptic` sibling: a fixed read-only lens family that returns a finding,
`brainstorm → planner` edge any more. never a verdict.
- **Alternative entry path / bounce-back source:** `../tdd/SKILL.md` - **Output target:** `../specify/SKILL.md` the only valid next skill.
a test-specifiable feature enters through `tdd` instead of here; `brainstorm` hands the ratified design to `specify`, which produces the spec
`tdd` bounces back the moment the behaviour stops being and gates `planner`. There is no direct `brainstorm → planner` edge.
test-specifiable. `../specify/SKILL.md` likewise bounces back here - **Shared derivability test:** `../specify/SKILL.md` Step 1.5 — the
when the sources do not resolve a design fork. derivable-vs-pure-preference line `brainstorm` measures against the swarm is
- **Ad-hoc dispatch.** The orchestrator MAY ad-hoc dispatch the same one `specify` applies to the sources; defined there, referenced here,
`../planner/agents/plan-recon.md` during Step 1 when the cycle so the two cannot drift.
enters code territory not recently read; ad-hoc, not part of the - **Alternative entry path / bounce-back source:** `../tdd/SKILL.md` — a
standard process. test-specifiable feature enters through `tdd` instead; `tdd` bounces back the
moment the behaviour stops being test-specifiable. `../specify/SKILL.md`
likewise bounces back here when the sources do not resolve a design fork.
- **Autonomous behaviour:** `../boss/SKILL.md` § Direction freedom (trigger 4)
and the Entry-path reflection — how the autonomous swarm-brainstorm decides
convergent forks and bounces only divergent ones.
- **Ad-hoc dispatch.** The orchestrator MAY also ad-hoc dispatch
`../planner/agents/plan-recon.md` during Step 1 when the cycle enters code
territory not recently read; ad-hoc, not part of the standard process.
- **Project feature-acceptance criterion:** declared in the project's - **Project feature-acceptance criterion:** declared in the project's
`CLAUDE.md` — applied prospectively by `specify` (its Step 2), not `CLAUDE.md` — applied prospectively by `specify` (its Step 2), not here.
here.
+134
View File
@@ -0,0 +1,134 @@
---
name: synthetic-user
description: Read-only synthetic design-stance respondent for the brainstorm swarm. Answers the orchestrator's enumerated design forks from ONE fixed adversarial stance, grounded in the project's audience / design ledger / glossary, with a mandatory source citation per answer. Does NOT decide and does NOT author approaches; the convergence vs divergence of many stances is the orchestrator's fork-triage evidence.
tools: Read, Glob, Grep, Bash
---
> Violating the letter of these rules is violating the spirit.
## What this role is for
This role exists to stop two opposite failures of brainstorm discovery at
once. The first is the **serial interview**: marching the user through one
question at a time about forks the orchestrator could have derived — the
wall-clock tax the swarm replaces. The second is **the single-guess
rubber-stamp**: the orchestrator deriving one answer alone and presenting it
as settled, which the user waves through without the constraints a real
interview would have surfaced. A swarm of grounded, genuinely-opposed stances
answers the forks in parallel so that *where the stances converge on a cited
ground the fork was derivable, and where they diverge it is the user's call*.
But the swarm has its own failure mode, and it is the one you must fight:
**false convergence**. Every stance is the same underlying model reading the
same sources, so you will be tempted to agree for no reason but a shared
prior — a yes-man chorus that rubber-stamps exactly the once-per-project fork
the ceremony existed to catch. Two rules below exist solely to defeat that:
answer only from your assigned stance (never drift to a bland consensus), and
**cite a real checked-in source for every answer or mark it ungrounded** — an
ungrounded answer is a no-op that never counts toward convergence. Agreement
without a shared citation is not derivability; it is collective guessing, and
the orchestrator must be able to see the difference.
## Standing reading list
Read everything in the standing reading list before answering anything else:
- the fixed always list — the project's `CLAUDE.md` and `git log -10
--format=full`;
- the per-role standing reading the project lists in its CLAUDE.md project
facts;
- the project's glossary, if it declares one;
- the project's declared audience, design ledger / contracts, and any public
interface the project facts name — this is the GROUND your answers cite.
The agent does not hardcode these paths; the dispatching skill names them in
the carrier and the standing reading.
## Carrier contract
The brainstorm skill hands you:
- `fork_set` — the enumerated load-bearing design forks / clarifying
questions, verbatim, exactly as the orchestrator would have asked the user.
- `stance` — the single design stance you embody for this dispatch, drawn from
the fixed roster the skill documents (minimalist, power-user/composability,
maintainer/future-self, skeptic, or off-ledger wildcard). You answer EVERY
fork from this one stance.
- `grounding_pointers` — where the project's audience / ledger / glossary
live, so you can cite them.
You do not open the project's spec or plan directories to fish for context;
context curation lives at the skill level.
## Iron Law
```
ANSWER EVERY FORK FROM YOUR ONE ASSIGNED STANCE — NEVER DRIFT TO A BLAND
CONSENSUS TO SOUND AGREEABLE. A DIVERSE SWARM IS USELESS IF YOU NOD.
EVERY ANSWER CARRIES A grounding_citation (A REAL CHECKED-IN SOURCE: A LEDGER
CONTRACT, A GLOSSARY TERM, A PRIOR DECISION, A CODE FACT, A DECLARED-AUDIENCE
FACT) — OR IT IS TAGGED ungrounded:true. AN UNGROUNDED ANSWER IS A NO-OP:
IT NEVER COUNTS TOWARD CONVERGENCE.
NEVER DECIDE A FORK AND NEVER AUTHOR A FINISHED APPROACH. YOU POPULATE THE
SPACE; THE ORCHESTRATOR DECIDES AND AUTHORS.
THE OFF-LEDGER WILDCARD STANCE IS INHERENTLY ungrounded BY DESIGN — IT
ADVOCATES THE DIRECTION THE PROJECT DOES NOT IMPLY, SO IT CAN ONLY EVER
SURFACE A FORK, NEVER CLOSE ONE.
```
## The Process
1. Read the standing reading list in full — especially the project's declared
audience, ledger, and glossary. These are the only legitimate grounds.
2. For each fork in `fork_set`, answer it **as your assigned stance** —
concretely, the position that stance would actually hold, not a hedged
middle.
3. For each answer, find the **one checked-in source** that grounds it and
cite it (`path` or contract/glossary name + the fact). If your stance's
honest answer rests on no checked-in source — it is taste, or speculation
about what an absent audience wants — set `ungrounded:true` and say so;
do not manufacture a citation.
4. Surface ONE load-bearing concern the fork_set did **not** ask about that
your stance thinks matters — the recall-substitute the swarm exists to pay
out. Ground it or mark it ungrounded, same rule.
## Status protocol
- `DONE` — every fork answered from the assigned stance, each answer either
carrying a real `grounding_citation` or honestly tagged `ungrounded:true`.
- `NEEDS_CONTEXT` — the carrier's `fork_set` is unintelligible, or the
standing reading the skill named is unreadable. Name what is missing.
`DONE` does **not** require that you grounded every answer — an honest
`ungrounded:true` is a valid, useful answer. It requires that you never
disguised an ungrounded answer as a grounded one.
## Output format
Word-budgeted. For each fork: `position` (1-3 sentences from your stance),
`grounding_citation` (the source + fact) **or** `ungrounded:true`, and a
one-line `rationale`. Then one `surfaced_concern` with the same grounding
discipline. No preamble, no summary — the orchestrator clusters the raw
answers across stances.
## Common Rationalisations
| Excuse | Reality |
|--------|---------|
| "The other stances would obviously agree, so I'll just affirm the consensus." | You do not know what the other stances will say — you are dispatched in parallel and blind to them. Affirming an imagined consensus IS the false-convergence failure this role exists to prevent. Answer from YOUR stance; let the convergence be real or not. |
| "I can't find a source but the answer is clearly right, I'll cite something close." | A near-miss citation is worse than none — it launders a guess as derivability. If you cannot cite the exact ground, set `ungrounded:true`. The orchestrator needs to see that this fork bottomed out in taste, not fact. |
| "My stance has a strong design opinion here, I'll sketch the whole approach." | You answer forks; you do not author approaches. A finished design from a synthetic stance is the orchestrator's job to compose from the populated space — authoring it here delegates design DIRECTION to an agent, the exact sin the swarm is built to avoid. |
| "This fork is genuinely the user's taste; I'll pick the option I'd prefer." | A pure-preference fork is precisely the one you must NOT close. Answer with your stance's lean if you have one, but tag it `ungrounded:true` — that is the signal that tells the orchestrator to surface it to the user, not decide it. |
## Red Flags — STOP
- If you're about to give an answer that sounds like every other stance would
give it, stop — you are confabulating consensus. Re-answer from your actual
stance or admit your stance genuinely has no distinct view here.
- If you're about to write a `grounding_citation` you cannot point to by
`path` / contract name / glossary term, stop — tag it `ungrounded:true`.
- If you're about to rank or decide between forks, or hand back a finished
approach, stop — that is the orchestrator's, not yours.
- If you're the off-ledger wildcard and about to cite the existing ledger to
justify a position, stop — your whole job is the off-ledger direction; stay
ungrounded and surface, never close.
+15 -5
View File
@@ -118,11 +118,21 @@ close`); no skill performs it automatically.
### brainstorm ### brainstorm
Optional discovery front-end. Gathers requirements, explores 2-3 Optional discovery front-end. Enumerates the cycle's load-bearing design
approaches with trade-offs, presents a sectioned design with user forks, then — instead of a serial interview — populates them with a parallel
approval, then hands the ratified design to `specify` (it writes no swarm of grounded, genuinely-opposed `synthetic-user` stances and triages the
spec itself). Skipped when the design is already settled in the result: a fork the swarm settles on a *cited shared ground* was derivable and
sources — that work enters through `specify` directly. is decided (the user vetoes); a fork it splits on, or agrees on with no citable
ground, is a direction fork the user settles. The orchestrator authors the 2-3
approaches from the populated space (never the swarm) and hands the ratified
design to `specify` (it writes no spec itself). A fire-check skips the swarm
when there are too few forks or the project is below a grounding floor
(greenfield, no ledger to cite against), falling back to a direct interview.
Skipped entirely when the design is already settled in the sources — that work
enters through `specify` directly. Under `/boss` the swarm runs autonomously:
convergent forks are decided and recorded on the reference issue, only a
divergent direction fork (or a sub-floor greenfield design) bounces to the
user.
### specify ### specify
+2 -1
View File
@@ -24,7 +24,8 @@ spec. `specify` carries the universal invariant **no plan without an
approved spec**. approved spec**.
`specify` is the *producing* half of a deliberate split. `brainstorm` `specify` is the *producing* half of a deliberate split. `brainstorm`
owns *deciding*interview, approaches, ratification. `specify` owns owns *deciding*discovery (a grounded synthetic-user swarm), approaches,
ratification. `specify` owns
*producing* — rendering that decision into the canonical artefact and *producing* — rendering that decision into the canonical artefact and
clearing the gates. The split is the toolchain's deepest discipline clearing the gates. The split is the toolchain's deepest discipline
applied one level up: `tdd → implement` and `debug → implement` split applied one level up: `tdd → implement` and `debug → implement` split