Prospect — upstream-of-plan idea generation
Read workflow.md for full phase-by-phase execution.
Generate many candidate ideas grounded in the repo, critique every one with explicit rejection reasons, and surface only the survivors bucketed by leverage. Output is a ranked artifact under .flow/prospects/<slug>-<date>.md that feeds directly into /flow-next:interview or /flow-next:plan via flowctl prospect promote.
Role: idea-prospecting coordinator (sequential single-chat — generate → critique → rank → write → handoff). Personas are prompt-level scaffolding inside this skill, not parallel subagent dispatch.
Preamble
CRITICAL: flowctl is BUNDLED — NOT installed globally. which flowctl will fail (expected). Define once; subsequent blocks (here and in workflow.md) use $FLOWCTL:
FLOWCTL="${DROID_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT}}/scripts/flowctl"
[ -x "$FLOWCTL" ] || FLOWCTL=".flow/bin/flowctl"
Inline skill (no context: fork) — keeps AskUserQuestion available throughout. Subagents can't call blocking question tools (Claude Code issues #12890, #34592), and Phases 0 + 6 both require user choice. (sync-codex.sh rewrites this to a plain-text numbered prompt in the Codex mirror.)
Input
Arguments: $ARGUMENTS
Format: [focus hint] — freeform single string. Optional. May be:
- Concept —
DX improvements,review-skill polish,test-suite health - Path —
plugins/flow-next/skills/(ideate inside a subtree) - Constraint —
quick wins under 200 LOC,minor-bump only,no new deps - Volume hint —
top 3(exactly 3 survivors),50 ideas(generate ≥50),raise the bar(60-70% rejection target)
If empty, the skill picks its own coverage targets (15-25 candidates → 5-8 survivors).
Ralph-block (R8)
/flow-next:prospect is exploratory and human-in-the-loop. Autonomous loops have no business deciding what a repo should tackle next — that's a judgement call. Hard-error with exit 2 when running under Ralph.
if [[ -n "${REVIEW_RECEIPT_PATH:-}" || "${FLOW_RALPH:-}" == "1" ]]; then
echo "Error: /flow-next:prospect requires a user at the terminal; not compatible with Ralph mode (REVIEW_RECEIPT_PATH or FLOW_RALPH detected)." >&2
exit 2
fi
No env-var opt-in. Ralph never decides direction.
Workflow
Execute the phases in workflow.md in order:
- Resume check — list active artifacts <30d; ask extend / fresh / open via blocking question. Corrupt artifacts surfaced but never offered for extension.
- Ground — scan repo with graceful degradation: git log (30d), open specs, CHANGELOG top, memory matches, memory audit (if present), strategy snapshot (verbatim
name/target_problem/approach/tracks/last_updatedfromflowctl strategy read --jsonwhensections_filled >= 1; husk-vs-presence gate usessections_filled, NOT[[ -f STRATEGY.md ]]). Emit a structured 30-50 line snapshot — titles + tags only, never raw bodies. - Generate — divergent-convergent + persona seeding (≥2 of
senior-maintainer/first-time-user/adversarial-reviewer, picked by focus hint per personas.md). One divergent prompt; no self-judging. - Critique — separate prompt pass that does NOT see the focus hint or persona texts; rejection floor ≥40% (≥60% under
raise the bar); fixed taxonomy (duplicates-open-epic | out-of-scope | out-of-scope-vs-strategy | insufficient-signal | too-large | backward-incompat | other);out-of-scope-vs-strategyis advisory only (user can override at promote time via existing--forceflag); floor violation surfaces blocking question with frozen optionsregenerate | loosen-floor | ship-anyway. - Rank — bucketed: high leverage 1-3, worth-considering 4-7, if-you-have-the-time 8+. Forced-format leverage sentence per survivor (
Small-diff lever because X; impact lands on Y.); no numeric scores. - Write artifact — atomic write-then-rename to
.flow/prospects/<slug>-<date>.mdviaflowctl.write_prospect_artifact. Same-day collisions suffix with-2,-3. Optionalfloor_violation/generation_under_volumeflags round-trip when upstream phases set them. - Handoff — blocking prompt for promote / interview / skip via the platform's question tool; frozen numbered-options fallback when no blocking tool is available.
Phases 0-6 are implemented. Promote command + list/read/archive land in tasks 4-5.
Pre-check: Local setup version
Compare .flow/meta.json setup_version to the plugin version; on mismatch, escalate once per plugin version. Fail-open throughout: a missing jq, .flow/meta.json, or plugin manifest silently continues.
SETUP_VER=$(jq -r '.setup_version // empty' .flow/meta.json 2>/dev/null)
PLUGIN_JSON="${DROID_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT}}/.claude-plugin/plugin.json"
PLUGIN_VER=$(jq -r '.version' "$PLUGIN_JSON" 2>/dev/null || echo "unknown")
VERSION_ACK=$(jq -r '.version_ack // empty' .flow/meta.json 2>/dev/null)
if [[ -n "$SETUP_VER" && "$PLUGIN_VER" != "unknown" && "$SETUP_VER" != "$PLUGIN_VER" ]]; then
if [[ "${FLOW_RALPH:-}" == "1" || -n "${REVIEW_RECEIPT_PATH:-}" \
|| "${FLOW_AUTONOMOUS:-}" == "1" || "${ARGUMENTS:-}" == *mode:autonomous* \
|| "$VERSION_ACK" == "$PLUGIN_VER" ]]; then
echo "Local setup v${SETUP_VER} differs from plugin v${PLUGIN_VER}. Run /flow-next:setup to refresh local scripts." >&2
else
echo "FLOW_SETUP_ASK ${SETUP_VER} ${PLUGIN_VER}"
fi
fi
If the block printed a FLOW_SETUP_ASK line, before proceeding ask the user with AskUserQuestion (local setup differs from the plugin; refresh now?), offering exactly the options Refresh now, Remind me next version, Skip this run, then continue the skill whichever is chosen:
- Refresh now: pause and have the user run
/flow-next:setupin this session (do not run setup yourself), then continue once it finishes. - Remind me next version: record the acknowledgement so this version is not re-asked (only a later plugin version re-arms it), then continue. Run this self-contained write (fail-open: on any error, continue anyway):
PJ="${DROID_PLUGIN_ROOT:-${CLAUDE_PLUGIN_ROOT}}/.claude-plugin/plugin.json" PV=$(jq -r '.version' "$PJ" 2>/dev/null) [[ -n "$PV" && "$PV" != "null" ]] && rm -f .flow/meta.json.tmp && jq --arg v "$PV" '.version_ack = $v' .flow/meta.json > .flow/meta.json.tmp && mv .flow/meta.json.tmp .flow/meta.json - Skip this run: continue without writing anything; the next invocation asks again.
Any other output (the one-line differs notice, or nothing) is non-blocking: continue.
Forbidden
- Running under Ralph — hard-block via the guard above.
- Setting
context: fork— blocking question tools must stay reachable. - Network calls — grounding is local-filesystem only (git, flowctl, memory, CHANGELOG).
- Writing to
.flow/specs/directly — onlyflowctl prospect promotemay do that. - Auto-archiving artifacts — only the explicit
prospect archivesubcommand moves files. - Dumping raw file bodies into the grounding snapshot — titles + tags only; structured 30-50 lines max.