From waterfall
Starts a new SDD need via the waterfall workflow — agent teams preflight, TeamCreate, OR spawn, bootstrap_need.
How this skill is triggered — by the user, by Claude, or both
Slash command
/waterfall:wf-newThis skill is limited to the following tools:
The summary Claude sees in its skill listing — used to decide when to auto-load this skill
This skill is the **entry point** of the waterfall workflow for a new need. It is invoked by the `/waterfall:new` slash command. Its sole role: prepare the environment, resolve the name, and hand off to OR.
This skill is the entry point of the waterfall workflow for a new need. It is invoked by the /waterfall:new slash command. Its sole role: prepare the environment, resolve the name, and hand off to OR.
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-check-bash.sh
If exit ≠ 0: display the error to HO and stop. The plugin requires bash (Git Bash on Windows).
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-check-teams.sh
If exit ≠ 0: display the error to HO and stop. The flag CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS=1 is required (see README.md Prerequisites).
jq is used by all wf scripts to parse .wf-state.json, ack-registry.json, etc.
INSTALL_CMD=$(bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-check-jq.sh) || JQ_RC=$?
jq missing. $INSTALL_CMD contains the install command adapted to the detected OS (empty if no known package manager).
INSTALL_CMD non-empty → AskUserQuestion: "jq is required. Install it now via ${INSTALL_CMD}?" (Yes / No).
bash -c "$INSTALL_CMD" then re-run wf-check-jq.sh. If still missing → display stderr and stop.INSTALL_CMD empty → display stderr (manual instructions + URL) and stop.The name is resolved by PM (main conversation) before any spawn — PM has the fresh verbal context from HO.
$ARGUMENTS provided → validate kebab-case, use directly as <name>$ARGUMENTS empty:
a. AskUserQuestion (open question): "Describe your need in a few words."
b. Generate 3 kebab-case proposals (2-4 words, semantically relevant)
c. AskUserQuestion with the 3 options (HO can also enter a free-form name)
d. Validate the chosen name: strict kebab-casels wf/needs/<name>/ → if it exists, AskUserQuestion to confirm overwrite or pick another nameRule: one question at a time to HO.
source ${CLAUDE_PLUGIN_ROOT}/scripts/wf-read-config.sh || {
echo "Invalid config — bootstrap stopped. Fix .wf-config.json or re-run /waterfall:config."
exit 2
}
The script emits a markdown summary of the resolved config on stdout (visible in the tool result) and exits 2 if a value is invalid. On error: display the summary to HO and stop the bootstrap.
# Copy templates by language (WF_LANGUAGE auto-detected from $LANG by wf-read-config.sh)
TEMPLATES_SRC="${CLAUDE_PLUGIN_ROOT}/wf/templates/${WF_LANGUAGE}"
[[ ! -d "$TEMPLATES_SRC" ]] && TEMPLATES_SRC="${CLAUDE_PLUGIN_ROOT}/wf/templates/en"
cp "$TEMPLATES_SRC"/*.md "wf/needs/<name>/"
IF WF_AGENT_MODE == "subagent-light":
→ Load wf-pm-light via Skill({name: "waterfall:wf-pm-light"})
→ The main conversation adopts PM-light responsibilities
→ Skip directly to Step 4.ter (no TeamCreate, no pré-spawn)
ELSE:
→ Load wf-pm via Skill({name: "wf-pm"})
→ Continue to Step 4
if [[ "$WF_AGENT_MODE" == "team" ]]; then
# Default mode
TeamCreate wf-<name>
elif [[ "$WF_AGENT_MODE" == "subagent-light" ]]; then
# subagent-light: no TeamCreate, no team, no inter-agent watchdog
# Inform HO: "Subagent-light mode active — 2 agents (PM+TL), 3 artefacts, 3 interactions HO"
: # no-op — proceed to Step 4.ter
else
# Subagent mode (ADR-006): no TeamCreate, agents are spawned via Agent tool
# Inform HO: "Subagent mode active — SendMessage and inter-agent watchdog disabled"
fi
One single team per Claude Code session (platform constraint). If a wf-* team already exists, escalate to HO before continuing.
.team-registry.json (traceability, optional)PM may initialize the traceability registry:
mkdir -p wf/needs/<name>
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-registry.sh init <name>
DEC-001: this registry is traceability only — the
wf-auth.shhook readsagent_typefrom the harness payload directly. Init is no longer a prerequisite to--completeenforcement.
wf-orchestrate.sh --init (PM, AVANT tout spawn) — EX-005 / B3PM exécute
--initAVANT le spawn d'OR (ou TL en mode subagent-light). Au moment où l'agent reçoit son brief,.wf-state.jsonexiste déjà.
# Mode team / subagent
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> \
--init --team wf-<name> --session "${CLAUDE_SESSION_ID}" \
--agent-mode "${WF_AGENT_MODE}" --dark-factory "${WF_DARK_FACTORY}"
# Mode subagent-light — pas de team, R-002 résolu : handle_init accepte toute valeur --team
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> \
--init --team "none" --session "${CLAUDE_SESSION_ID}" \
--agent-mode "subagent-light" --dark-factory "${WF_DARK_FACTORY}"
Propagation config (fix bug-3eec8bce) : les flags
--agent-modeet--dark-factoryoverrident les valeurs lues parhandle_initdepuis.wf-config.json. Source de vérité = les env vars résolues au Step 2.bis parwf-read-config.sh, pas le fichier projet (qui peut être absent).
Idempotence (TF-021) — si .wf-state.json existe déjà :
.wf-state.json n'est pas corrompu, aucun artéfact métier modifié.Critère opposable (TF-010) : après cette étape, wf/needs/<name>/.wf-state.json
existe et contient phase, step, session_id non nul.
Subagent et subagent-light. En mode team, ces 2 steps sont complétés par le PM teammate après que OR ait émis
PLEASE_COMPLETE_STEP. En mode subagent/subagent-light, PM = main agent (hors team), donc OR ne peut pas le contacter viaSendMessage→ deadlock au BOOTSTRAP. PM doit donc pré-compléter ces steps avant le spawn de l'agent suivant (OR en subagent, TL en subagent-light).
if [[ "$WF_AGENT_MODE" == "subagent" || "$WF_AGENT_MODE" == "subagent-light" ]]; then
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> --complete BOOTSTRAP:DETERMINE_NAME
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> --complete BOOTSTRAP:RUN_BOOTSTRAP
fi
En mode subagent : après ces 2 --complete, le state machine arrive à
BOOTSTRAP:COLLECT_CARD_NUM (agent=or). OR pilote à partir de là.
En mode subagent-light : après ces 2 --complete, _wf_auto_skip_light
skip automatiquement tous les steps agent=or (COLLECT_CARD_NUM, COLLECT_BRANCH_TYPE,
CREATE_BRANCH_Q, SPAWN_TEAM) jusqu'au premier step agent=pm ou agent=tl.
PM-light pilote directement sans OR intermédiaire.
subagent-light : pas de pré-spawn. PM-light spawne TL directement lors de la Phase D (après validation specs HO). Aucun OR, PO, RV, QA, DS spawné (EX-018, TF-017). Sauter ce step en mode subagent-light et laisser PM-light piloter.
PM pré-spawne en UN SEUL BATCH la team fixe avant de transférer le pilotage à OR (modes team et subagent uniquement). OR ne pilote plus le spawn (cf. EX-004 — tool
Agentretiré du frontmatter d'OR). Aucunspawn_requestn'est émis par OR pour ces rôles fixes durant la totalité du workflow (TF-005).
Team fixe (toujours, team/subagent) : or, po, tl, rv, qa.
DS conditionnel : ajouté au batch ssi PRD.md frontmatter porte has_ui: true (TF-004).
DV : non spawné ici. Émission lazy après PLANNING:CHECKPOINT_TASKS (cf. Step 9).
# Mode subagent-light — SKIP this step entirely. PM-light handles TL spawn in Phase D.
# Mode team
TeamCreate already done at Step 4 → spawn each role as teammate
in a single PM turn (5 ou 6 spawns), with model=$WF_MODEL_<role>.
# Mode subagent
Single PM turn with N parallel Agent() calls:
Agent(subagent_type: wf-or, prompt: <bootstrap_need>)
Agent(subagent_type: wf-po, prompt: <stand-by — wait for OR brief>)
Agent(subagent_type: wf-tl, prompt: <stand-by>)
Agent(subagent_type: wf-rv, prompt: <stand-by>)
Agent(subagent_type: wf-qa, prompt: <stand-by>)
# if PRD.has_ui == true:
Agent(subagent_type: wf-ds, prompt: <stand-by>)
Critère opposable (TF-003 / TF-004) : à la sortie de BOOTSTRAP:SPAWN_TEAM,
wf/needs/<name>/.team-registry.json contient or, po, tl, rv, qa (et ds si
has_ui:true), pas dv.
System-critical (team mode only): the cron wakes PM up to detect STUCK teammates. Skipped in subagent mode — subagents are not idle between messages (they resume on each SendMessage), so there is no "idle-muet teammate" to repoke; PM stays in charge of every spawn and already knows the workflow state.
if [[ "$WF_AGENT_MODE" == "subagent" ]]; then
# No watchdog in subagent mode (no idle teammates to wake up).
# HO message: "Watchdog skipped (agent_mode=subagent)"
:
elif [[ "$WF_WATCHDOG_INTERVAL" != "off" ]]; then
DELAY_MIN="${WF_WATCHDOG_INTERVAL//min/}" # "3min" → "3"
# 1. PM invokes CronCreate (harness tool)
CronCreate(cron: "*/${DELAY_MIN} * * * *", prompt: "watchdog tick wf-<name>", recurring: true)
# 2. Touch the marker with the returned job_id — OR uses it to verify (safety net)
echo "<cron_job_id>" > wf/needs/<name>/.watchdog-cron-active
# HO message: "Watchdog active (${WF_WATCHDOG_INTERVAL})"
fi
If PM forgets this step (team mode only): OR detects the absence of .watchdog-cron-active and creates the cron itself (see agents/wf-or.md §Watchdog — belt-and-suspenders).
For spawn traceability:
bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-registry.sh add <name> <or_agent_id> or
DEC-001: traceability only — enforcement uses
agent_typefrom the payload. Skipping this step does not prevent OR from completing its steps.
intent + context_files) — EX-001 / F1Discipline brief opposable (INV-005) :
intent:+context_files:, corps horscontext_files:< 20 lignes, pas de paraphrase de PRD.md. Gabarit aligné suragents/wf-pm.md §Gabarits de briefs(T-003).
PM envoie à OR (à la sortie du batch Step 5) un seul bootstrap_need :
type: bootstrap_need
need: <name>
intent: <1 phrase ≤ 200 caractères — la mission HO synthétisée>
context_files:
- wf/needs/<name>/PRD.md
config:
agent_mode: <subagent|team>
dark_factory: <on|off>
language: <fr|en>
watchdog_interval: <WF_WATCHDOG_INTERVAL>
models: { or, po, tl, rv, qa, dv, ds }
review_loops: { artifacts, code }
# corps libre ≤ 20 lignes — pas de paraphrase de PRD.md
Critère opposable (TF-001) : champ intent: ≤ 200 caractères, champ
context_files: non vide, corps hors context_files: < 20 lignes, aucune
duplication du contenu de PRD.md.
OR enchaîne directement sur --query (l'init a été fait au Step 4.ter par PM —
pas de double-init côté OR).
Déclencheur : juste après
PLANNING:CHECKPOINT_TASKSvalidé. Cette étape est portée par PM (cf.agents/wf-pm.md §Responsabilité — DV-lazy batchpour l'algo détaillé).
Résumé de l'étape :
wf/needs/<name>/tasks.md → liste tâches DV + dépendances.N = max(parallélisme du chemin critique) ; plafond
.wf-config.json:planning.max_dv si défini.bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> --log \
--msg "[DV-LAZY] N=<N> justification=<critical_path_width=K|max_dv=K> tasks=<count>"
Critère opposable (TF-015 / TF-016) :
PLANNING:CHECKPOINT_TASKS.[DV-LAZY] N=<N> dans or.log après le checkpoint.Déclencheur : juste après le DV-lazy batch (Step 9), avant que les DVs commencent à implémenter. Cette étape est portée par PM (cf.
agents/wf-pm.md §Dashboard TaskCreate batchpour l'algorithme détaillé). Non applicable en modesubagent-light(EX-006 dv-tasks-dashboard).
Résumé de l'étape :
wf/needs/<name>/tasks.md → liste les lignes T-xxx.TaskCreate pour chaque T-xxx avec :
subject = titre T-xxx,description = cellule Description de la ligne,metadata.t_id = "T-xxx" (lookup ultérieur).{t_id → taskId} retournée par CC.bash ${CLAUDE_PLUGIN_ROOT}/scripts/wf-orchestrate.sh <name> --log \
--msg "[DASHBOARD] TaskCreate batch tasks=<N>"
Les status sont ensuite mis à jour par PM via TaskUpdate au fil des
t_status_update reçus (relay mode team) ou des marqueurs [T_STATUS]
trouvés dans l'output des Agent calls (mode subagent). Mapping
INV-007 → CC status défini dans agents/wf-pm.md §Dashboard TaskCreate batch.
Critère opposable : après cette étape, la TaskList de la conversation PM
contient exactement N tasks pending, chacune avec metadata.t_id unique
tracé à tasks.md.
wf/needs/<name>/wf/needs/<name>/ before spawn$HOME/.claude/wf-session-active.<session_id> after --init (session-scoped marker, required by /waterfall:resume). The session_id is $WF_SID resolved in step 1.bis, passed via --session. No leadSessionId or "default" fallback (EX-010, INV-002).--team + --session: wf-orchestrate.sh <name> --init --team wf-<name> --session "$WF_SID" — WF_SID is the only source of truth for the HO sid (EX-006, ADR-001).IMPORTANT — SendMessage plain text obligatoire : le paramètre
messagedeSendMessagen'accepte questring. Utiliser le format plain textclé: valeur— jamais d'objet{...}, jamaisJSON.stringify().
npx claudepluginhub mgallet92i/waterfall --plugin waterfallGuides creation, editing, and verification of skills for AI coding agents using test-driven development with subagent scenarios. Use when authoring or debugging skills.