From 18bb0149c8d4e0133a55f45dc935bbe4788e77ee Mon Sep 17 00:00:00 2001 From: Tom Boucher Date: Sat, 21 Mar 2026 00:21:17 -0400 Subject: [PATCH] feat: add workflow.discuss_mode assumptions config (#637) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add codebase-first assumption-driven alternative to the interview-style discuss-phase. New `workflow.discuss_mode: "assumptions"` config routes to a separate workflow that spawns a gsd-assumptions-analyzer agent to read 5-15 codebase files, surface assumptions with evidence, and ask only for corrections (~2-4 interactions vs ~15-20). - New gsd-assumptions-analyzer agent for deep codebase analysis - New discuss-phase-assumptions.md workflow (15 steps) - Command-level routing via dual @reference + process gate - Identical CONTEXT.md output — downstream agents unaffected - Existing discuss-phase.md workflow untouched (zero diff) - Mode-aware plan-phase gate and progress display - User documentation and integration tests - Update agent count and list in copilot-install tests (17 → 18) Closes #637 Co-Authored-By: Claude Opus 4.6 (1M context) --- agents/gsd-assumptions-analyzer.md | 105 +++ commands/gsd/discuss-phase.md | 14 +- docs/workflow-discuss-mode.md | 68 ++ get-shit-done/templates/config.json | 3 +- .../workflows/discuss-phase-assumptions.md | 645 ++++++++++++++++++ get-shit-done/workflows/plan-phase.md | 8 + get-shit-done/workflows/progress.md | 5 + tests/copilot-install.test.cjs | 7 +- tests/discuss-mode.test.cjs | 101 +++ 9 files changed, 951 insertions(+), 5 deletions(-) create mode 100644 agents/gsd-assumptions-analyzer.md create mode 100644 docs/workflow-discuss-mode.md create mode 100644 get-shit-done/workflows/discuss-phase-assumptions.md create mode 100644 tests/discuss-mode.test.cjs diff --git a/agents/gsd-assumptions-analyzer.md b/agents/gsd-assumptions-analyzer.md new file mode 100644 index 00000000..5531fc4a --- /dev/null +++ b/agents/gsd-assumptions-analyzer.md @@ -0,0 +1,105 @@ +--- +name: gsd-assumptions-analyzer +description: Deeply analyzes codebase for a phase and returns structured assumptions with evidence. Spawned by discuss-phase assumptions mode. +tools: Read, Bash, Grep, Glob +color: cyan +--- + + +You are a GSD assumptions analyzer. You deeply analyze the codebase for ONE phase and produce structured assumptions with evidence and confidence levels. + +Spawned by `discuss-phase-assumptions` via `Task()`. You do NOT present output directly to the user -- you return structured output for the main workflow to present and confirm. + +**Core responsibilities:** +- Read the ROADMAP.md phase description and any prior CONTEXT.md files +- Search the codebase for files related to the phase (components, patterns, similar features) +- Read 5-15 most relevant source files +- Produce structured assumptions citing file paths as evidence +- Flag topics where codebase analysis alone is insufficient (needs external research) + + + +Agent receives via prompt: + +- `` -- phase number and name +- `` -- phase description from ROADMAP.md +- `` -- summary of locked decisions from earlier phases +- `` -- scout results (relevant files, components, patterns found) +- `` -- one of: `full_maturity`, `standard`, `minimal_decisive` + + + +The calibration tier controls output shape. Follow the tier instructions exactly. + +### full_maturity +- **Areas:** 3-5 assumption areas +- **Alternatives:** 2-3 per Likely/Unclear item +- **Evidence depth:** Detailed file path citations with line-level specifics + +### standard +- **Areas:** 3-4 assumption areas +- **Alternatives:** 2 per Likely/Unclear item +- **Evidence depth:** File path citations + +### minimal_decisive +- **Areas:** 2-3 assumption areas +- **Alternatives:** Single decisive recommendation per item +- **Evidence depth:** Key file paths only + + + +1. Read ROADMAP.md and extract the phase description +2. Read any prior CONTEXT.md files from earlier phases (find via `find .planning/phases -name "*-CONTEXT.md"`) +3. Use Glob and Grep to find files related to the phase goal terms +4. Read 5-15 most relevant source files to understand existing patterns +5. Form assumptions based on what the codebase reveals +6. Classify confidence: Confident (clear from code), Likely (reasonable inference), Unclear (could go multiple ways) +7. Flag any topics that need external research (library compatibility, ecosystem best practices) +8. Return structured output in the exact format below + + + +Return EXACTLY this structure: + +``` +## Assumptions + +### [Area Name] (e.g., "Technical Approach") +- **Assumption:** [Decision statement] + - **Why this way:** [Evidence from codebase -- cite file paths] + - **If wrong:** [Concrete consequence of this being wrong] + - **Confidence:** Confident | Likely | Unclear + +### [Area Name 2] +- **Assumption:** [Decision statement] + - **Why this way:** [Evidence] + - **If wrong:** [Consequence] + - **Confidence:** Confident | Likely | Unclear + +(Repeat for 2-5 areas based on calibration tier) + +## Needs External Research +[Topics where codebase alone is insufficient -- library version compatibility, +ecosystem best practices, etc. Leave empty if codebase provides enough evidence.] +``` + + + +1. Every assumption MUST cite at least one file path as evidence. +2. Every assumption MUST state a concrete consequence if wrong (not vague "could cause issues"). +3. Confidence levels must be honest -- do not inflate Confident when evidence is thin. +4. Minimize Unclear items by reading more files before giving up. +5. Do NOT suggest scope expansion -- stay within the phase boundary. +6. Do NOT include implementation details (that's for the planner). +7. Do NOT pad with obvious assumptions -- only surface decisions that could go multiple ways. +8. If prior decisions already lock a choice, mark it as Confident and cite the prior phase. + + + +- Do NOT present output directly to user (main workflow handles presentation) +- Do NOT research beyond what the codebase contains (flag gaps in "Needs External Research") +- Do NOT use web search or external tools (you have Read, Bash, Grep, Glob only) +- Do NOT include time estimates or complexity assessments +- Do NOT generate more areas than the calibration tier specifies +- Do NOT invent assumptions about code you haven't read -- read first, then form opinions + diff --git a/commands/gsd/discuss-phase.md b/commands/gsd/discuss-phase.md index 75ebde60..427077fa 100644 --- a/commands/gsd/discuss-phase.md +++ b/commands/gsd/discuss-phase.md @@ -1,7 +1,7 @@ --- name: gsd:discuss-phase description: Gather phase context through adaptive questioning before planning. Use --auto to skip interactive questions (Claude picks recommended defaults). -argument-hint: " [--auto] [--batch] [--analyze]" +argument-hint: " [--auto] [--batch] [--analyze] [--text]" allowed-tools: - Read - Write @@ -30,6 +30,7 @@ Extract implementation decisions that downstream agents need — researcher and @~/.claude/get-shit-done/workflows/discuss-phase.md +@~/.claude/get-shit-done/workflows/discuss-phase-assumptions.md @~/.claude/get-shit-done/templates/context.md @@ -40,6 +41,17 @@ Context files are resolved in-workflow using `init phase-op` and roadmap/state t +**Mode routing:** +```bash +DISCUSS_MODE=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-get workflow.discuss_mode 2>/dev/null || echo "discuss") +``` + +If `DISCUSS_MODE` is `"assumptions"`: **Follow the discuss-phase-assumptions.md workflow instead of the steps below.** Skip all remaining steps in this process section. + +If `DISCUSS_MODE` is `"discuss"` (or unset, or any other value): Continue with the steps below (current behavior). + +--- + 1. Validate phase number (error if missing or not in roadmap) 2. Check if CONTEXT.md exists (offer update/view/skip if yes) 3. **Load prior context** — Read PROJECT.md, REQUIREMENTS.md, STATE.md, and all prior CONTEXT.md files diff --git a/docs/workflow-discuss-mode.md b/docs/workflow-discuss-mode.md new file mode 100644 index 00000000..70aa6605 --- /dev/null +++ b/docs/workflow-discuss-mode.md @@ -0,0 +1,68 @@ +# Discuss Mode: Assumptions vs Interview + +GSD's discuss-phase has two modes for gathering implementation context before planning. + +## Modes + +### `discuss` (default) + +The original interview-style flow. Claude identifies gray areas in the phase, presents them +for selection, then asks ~4 questions per area. Good for: + +- Early phases where the codebase is new +- Phases where the user has strong opinions they want to express proactively +- Users who prefer guided, conversational context gathering + +### `assumptions` + +A codebase-first flow. Claude deeply analyzes the codebase via a subagent (reading 5-15 +relevant files), forms assumptions with evidence, and presents them for confirmation or +correction. Good for: + +- Established codebases with clear patterns +- Users who find the interview questions obvious +- Faster context gathering (~2-4 interactions vs ~15-20) + +## Configuration + +```bash +# Enable assumptions mode +gsd-tools config-set workflow.discuss_mode assumptions + +# Switch back to interview mode +gsd-tools config-set workflow.discuss_mode discuss +``` + +The setting is per-project (stored in `.planning/config.json`). + +## How Assumptions Mode Works + +1. **Init** — Same as discuss mode (load prior context, scout codebase, check todos) +2. **Deep analysis** — Explore subagent reads 5-15 codebase files related to the phase +3. **Surface assumptions** — Each assumption includes: + - What Claude would do and why (citing file paths) + - What goes wrong if the assumption is incorrect + - Confidence level (Confident / Likely / Unclear) +4. **Confirm or correct** — User reviews assumptions, selects any that need changing +5. **Write CONTEXT.md** — Identical output format to discuss mode + +## Flag Compatibility + +| Flag | `discuss` mode | `assumptions` mode | +|------|----------------|-------------------| +| `--auto` | Auto-selects recommended answers | Skips confirm gate, auto-resolves Unclear items | +| `--batch` | Groups questions in batches | N/A (corrections already batched) | +| `--text` | Plain-text questions (remote sessions) | Plain-text questions (remote sessions) | +| `--analyze` | Shows trade-off tables per question | N/A (assumptions include evidence) | + +## Output + +Both modes produce identical CONTEXT.md with the same 6 sections: +- `` — Phase boundary +- `` — Locked implementation decisions +- `` — Specs/docs downstream agents must read +- `` — Reusable assets, patterns, integration points +- `` — User references and preferences +- `` — Ideas noted for future phases + +Downstream agents (researcher, planner, checker) consume this identically regardless of mode. diff --git a/get-shit-done/templates/config.json b/get-shit-done/templates/config.json index 6b8b4606..f730fa68 100644 --- a/get-shit-done/templates/config.json +++ b/get-shit-done/templates/config.json @@ -6,7 +6,8 @@ "plan_check": true, "verifier": true, "auto_advance": false, - "nyquist_validation": true + "nyquist_validation": true, + "discuss_mode": "discuss" }, "planning": { "commit_docs": true, diff --git a/get-shit-done/workflows/discuss-phase-assumptions.md b/get-shit-done/workflows/discuss-phase-assumptions.md new file mode 100644 index 00000000..26d51a31 --- /dev/null +++ b/get-shit-done/workflows/discuss-phase-assumptions.md @@ -0,0 +1,645 @@ + +Extract implementation decisions that downstream agents need — using codebase-first analysis +and assumption surfacing instead of interview-style questioning. + +You are a thinking partner, not an interviewer. Analyze the codebase deeply, surface what you +believe based on evidence, and ask the user only to correct what's wrong. + + + +**CONTEXT.md feeds into:** + +1. **gsd-phase-researcher** — Reads CONTEXT.md to know WHAT to research +2. **gsd-planner** — Reads CONTEXT.md to know WHAT decisions are locked + +**Your job:** Capture decisions clearly enough that downstream agents can act on them +without asking the user again. Output is identical to discuss mode — same CONTEXT.md format. + + + +**Assumptions mode philosophy:** + +The user is a visionary, not a codebase archaeologist. They need enough context to evaluate +whether your assumptions match their intent — not to answer questions you could figure out +by reading the code. + +- Read the codebase FIRST, form opinions SECOND, ask ONLY about what's genuinely unclear +- Every assumption must cite evidence (file paths, patterns found) +- Every assumption must state consequences if wrong +- Minimize user interactions: ~2-4 corrections vs ~15-20 questions + + + +**CRITICAL: No scope creep.** + +The phase boundary comes from ROADMAP.md and is FIXED. Discussion clarifies HOW to implement +what's scoped, never WHETHER to add new capabilities. + +When user suggests scope creep: +"[Feature X] would be a new capability — that's its own phase. +Want me to note it for the roadmap backlog? For now, let's focus on [phase domain]." + +Capture the idea in "Deferred Ideas". Don't lose it, don't act on it. + + + +**IMPORTANT: Answer validation** — After every AskUserQuestion call, check if the response +is empty or whitespace-only. If so: +1. Retry the question once with the same parameters +2. If still empty, present the options as a plain-text numbered list + +**Text mode (`workflow.text_mode: true` in config or `--text` flag):** +When text mode is active, do not use AskUserQuestion at all. Present every question as a +plain-text numbered list and ask the user to type their choice number. + + + + + +Phase number from argument (required). + +```bash +INIT=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" init phase-op "${PHASE}") +if [[ "$INIT" == @file:* ]]; then INIT=$(cat "${INIT#@file:}"); fi +``` + +Parse JSON for: `commit_docs`, `phase_found`, `phase_dir`, `phase_number`, `phase_name`, +`phase_slug`, `padded_phase`, `has_research`, `has_context`, `has_plans`, `has_verification`, +`plan_count`, `roadmap_exists`, `planning_exists`. + +**If `phase_found` is false:** +``` +Phase [X] not found in roadmap. + +Use /gsd:progress to see available phases. +``` +Exit workflow. + +**If `phase_found` is true:** Continue to check_existing. + +**Auto mode** — If `--auto` is present in ARGUMENTS: +- In `check_existing`: auto-select "Update it" (if context exists) or continue without prompting +- In `present_assumptions`: skip confirmation gate, proceed directly to write CONTEXT.md +- In `correct_assumptions`: auto-select recommended option for each correction +- Log each auto-selected choice inline +- After completion, auto-advance to plan-phase + + + +Check if CONTEXT.md already exists using `has_context` from init. + +```bash +ls ${phase_dir}/*-CONTEXT.md 2>/dev/null +``` + +**If exists:** + +**If `--auto`:** Auto-select "Update it". Log: `[auto] Context exists — updating with assumption-based analysis.` + +**Otherwise:** Use AskUserQuestion: +- header: "Context" +- question: "Phase [X] already has context. What do you want to do?" +- options: + - "Update it" — Re-analyze codebase and refresh assumptions + - "View it" — Show me what's there + - "Skip" — Use existing context as-is + +If "Update": Load existing, continue to load_prior_context +If "View": Display CONTEXT.md, then offer update/skip +If "Skip": Exit workflow + +**If doesn't exist:** + +Check `has_plans` and `plan_count` from init. **If `has_plans` is true:** + +**If `--auto`:** Auto-select "Continue and replan after". Log: `[auto] Plans exist — continuing with assumption analysis, will replan after.` + +**Otherwise:** Use AskUserQuestion: +- header: "Plans exist" +- question: "Phase [X] already has {plan_count} plan(s) created without user context. Your decisions here won't affect existing plans unless you replan." +- options: + - "Continue and replan after" + - "View existing plans" + - "Cancel" + +If "Continue and replan after": Continue to load_prior_context. +If "View existing plans": Display plan files, then offer "Continue" / "Cancel". +If "Cancel": Exit workflow. + +**If `has_plans` is false:** Continue to load_prior_context. + + + +Read project-level and prior phase context to avoid re-asking decided questions. + +**Step 1: Read project-level files** +```bash +cat .planning/PROJECT.md 2>/dev/null +cat .planning/REQUIREMENTS.md 2>/dev/null +cat .planning/STATE.md 2>/dev/null +``` + +Extract from these: +- **PROJECT.md** — Vision, principles, non-negotiables, user preferences +- **REQUIREMENTS.md** — Acceptance criteria, constraints +- **STATE.md** — Current progress, any flags + +**Step 2: Read all prior CONTEXT.md files** +```bash +find .planning/phases -name "*-CONTEXT.md" 2>/dev/null | sort +``` + +For each CONTEXT.md where phase number < current phase: +- Read the `` section — these are locked preferences +- Read `` — particular references or "I want it like X" moments +- Note patterns (e.g., "user consistently prefers minimal UI") + +**Step 3: Build internal `` context** + +Structure the extracted information for use in assumption generation. + +**If no prior context exists:** Continue without — expected for early phases. + + + +Check if any pending todos are relevant to this phase's scope. + +```bash +TODO_MATCHES=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" todo match-phase "${PHASE_NUMBER}") +``` + +Parse JSON for: `todo_count`, `matches[]`. + +**If `todo_count` is 0:** Skip silently. + +**If matches found:** Present matched todos, use AskUserQuestion (multiSelect) to fold relevant ones into scope. + +**For selected (folded) todos:** Store as `` for CONTEXT.md `` section. +**For unselected:** Store as `` for CONTEXT.md `` section. + +**Auto mode (`--auto`):** Fold all todos with score >= 0.4 automatically. Log the selection. + + + +Lightweight scan of existing code to inform assumption generation. + +**Step 1: Check for existing codebase maps** +```bash +ls .planning/codebase/*.md 2>/dev/null +``` + +**If codebase maps exist:** Read relevant ones (CONVENTIONS.md, STRUCTURE.md, STACK.md). Extract reusable components, patterns, integration points. Skip to Step 3. + +**Step 2: If no codebase maps, do targeted grep** + +Extract key terms from phase goal, search for related files. + +```bash +grep -rl "{term1}\|{term2}" src/ app/ --include="*.ts" --include="*.tsx" 2>/dev/null | head -10 +``` + +Read the 3-5 most relevant files. + +**Step 3: Build internal ``** + +Identify reusable assets, established patterns, integration points, and creative options. Store internally for use in deep_codebase_analysis. + + + +Spawn a `gsd-assumptions-analyzer` agent to deeply analyze the codebase for this phase. This +keeps raw file contents out of the main context window, protecting token budget. + +**Resolve calibration tier (if USER-PROFILE.md exists):** + +```bash +PROFILE_PATH="$HOME/.claude/get-shit-done/USER-PROFILE.md" +``` + +If file exists at PROFILE_PATH: +- Priority 1: Read config.json > preferences.vendor_philosophy (project-level override) +- Priority 2: Read USER-PROFILE.md Vendor Choices/Philosophy rating (global) +- Priority 3: Default to "standard" + +Map to calibration tier: +- conservative OR thorough-evaluator → full_maturity (more alternatives, detailed evidence) +- opinionated → minimal_decisive (fewer alternatives, decisive recommendations) +- pragmatic-fast OR any other value → standard + +If no USER-PROFILE.md: calibration_tier = "standard" + +**Spawn Explore subagent:** + +``` +Task(subagent_type="gsd-assumptions-analyzer", prompt=""" +Analyze the codebase for Phase {PHASE}: {phase_name}. + +Phase goal: {roadmap_description} +Prior decisions: {prior_decisions_summary} +Codebase scout hints: {codebase_context_summary} +Calibration: {calibration_tier} + +Your job: +1. Read ROADMAP.md phase {PHASE} description +2. Read any prior CONTEXT.md files from earlier phases +3. Glob/Grep for files related to: {phase_relevant_terms} +4. Read 5-15 most relevant source files +5. Return structured assumptions + +## Output Format + +Return EXACTLY this structure: + +## Assumptions + +### [Area Name] (e.g., "Technical Approach") +- **Assumption:** [Decision statement] + - **Why this way:** [Evidence from codebase — cite file paths] + - **If wrong:** [Concrete consequence of this being wrong] + - **Confidence:** Confident | Likely | Unclear + +(3-5 areas, calibrated by tier: +- full_maturity: 3-5 areas, 2-3 alternatives per Likely/Unclear item +- standard: 3-4 areas, 2 alternatives per Likely/Unclear item +- minimal_decisive: 2-3 areas, decisive single recommendation per item) + +## Needs External Research +[Topics where codebase alone is insufficient — library version compatibility, +ecosystem best practices, etc. Leave empty if codebase provides enough evidence.] +""") +``` + +Parse the subagent's response. Extract: +- `assumptions[]` — each with area, statement, evidence, consequence, confidence +- `needs_research[]` — topics requiring external research (may be empty) + +**Initialize canonical refs accumulator:** +- Source 1: Copy `Canonical refs:` from ROADMAP.md for this phase, expand to full paths +- Source 2: Check REQUIREMENTS.md and PROJECT.md for specs/ADRs referenced +- Source 3: Add any docs referenced in codebase scout results + + + +**Skip if:** `needs_research` from deep_codebase_analysis is empty. + +If research topics were flagged, spawn a general-purpose research agent: + +``` +Task(subagent_type="general-purpose", prompt=""" +Research the following topics for Phase {PHASE}: {phase_name}. + +Topics needing research: +{needs_research_content} + +For each topic, return: +- **Finding:** [What you learned] +- **Source:** [URL or library docs reference] +- **Confidence impact:** [Which assumption this resolves and to what confidence level] + +Use Context7 (resolve-library-id then query-docs) for library-specific questions. +Use WebSearch for ecosystem/best-practice questions. +""") +``` + +Merge findings back into assumptions: +- Update confidence levels where research resolves ambiguity +- Add source attribution to affected assumptions +- Store research findings for DISCUSSION-LOG.md + +**If no gaps flagged:** Skip entirely. Most phases will skip this step. + + + +Display all assumptions grouped by area with confidence badges. + +**Format for display:** + +``` +## Phase {PHASE}: {phase_name} — Assumptions + +Based on codebase analysis, here's what I'd go with: + +### {Area Name} +{Confidence badge} **{Assumption statement}** +↳ Evidence: {file paths cited} +↳ If wrong: {consequence} + +### {Area Name 2} +... + +[If external research was done:] +### External Research Applied +- {Topic}: {Finding} (Source: {URL}) +``` + +**If `--auto`:** +- If all assumptions are Confident or Likely: log assumptions, skip to write_context. + Log: `[auto] All assumptions Confident/Likely — proceeding to context capture.` +- If any assumptions are Unclear: log a warning, auto-select recommended alternative for + each Unclear item. Log: `[auto] {N} Unclear assumptions auto-resolved with recommended defaults.` + Proceed to write_context. + +**Otherwise:** Use AskUserQuestion: +- header: "Assumptions" +- question: "These all look right?" +- options: + - "Yes, proceed" — Write CONTEXT.md with these assumptions as decisions + - "Let me correct some" — Select which assumptions to change + +**If "Yes, proceed":** Skip to write_context. +**If "Let me correct some":** Continue to correct_assumptions. + + + +The assumptions are already displayed above from present_assumptions. + +Present a multiSelect where each option's label is the assumption statement and description +is the "If wrong" consequence: + +Use AskUserQuestion (multiSelect): +- header: "Corrections" +- question: "Which assumptions need correcting?" +- options: [one per assumption, label = assumption statement, description = "If wrong: {consequence}"] + +For each selected correction, ask ONE focused question: + +Use AskUserQuestion: +- header: "{Area Name}" +- question: "What should we do instead for: {assumption statement}?" +- options: [2-3 concrete alternatives describing user-visible outcomes, recommended option first] + +Record each correction: +- Original assumption +- User's chosen alternative +- Reason (if provided via "Other" free text) + +After all corrections processed, continue to write_context with updated assumptions. + +**Auto mode:** Should not reach this step (--auto skips from present_assumptions). + + + +Create phase directory if needed. Write CONTEXT.md using the standard 6-section format. + +**File:** `${phase_dir}/${padded_phase}-CONTEXT.md` + +Map assumptions to CONTEXT.md sections: +- Assumptions → `` (each assumption becomes a locked decision: D-01, D-02, etc.) +- Corrections → override the original assumption in `` +- Areas where all assumptions were Confident → marked as locked decisions +- Areas with corrections → include user's chosen alternative as the decision +- Folded todos → included in `` under "### Folded Todos" + +```markdown +# Phase {PHASE}: {phase_name} - Context + +**Gathered:** {date} (assumptions mode) +**Status:** Ready for planning + + +## Phase Boundary + +{Domain boundary from ROADMAP.md — clear statement of scope anchor} + + + +## Implementation Decisions + +### {Area Name 1} +- **D-01:** {Decision — from assumption or correction} +- **D-02:** {Decision} + +### {Area Name 2} +- **D-03:** {Decision} + +### Claude's Discretion +{Any assumptions where the user confirmed "you decide" or left as-is with Likely confidence} + +### Folded Todos +{If any todos were folded into scope} + + + +## Canonical References + +**Downstream agents MUST read these before planning or implementing.** + +{Accumulated canonical refs from analyze step — full relative paths} + +[If no external specs: "No external specs — requirements fully captured in decisions above"] + + + +## Existing Code Insights + +### Reusable Assets +{From codebase scout + Explore subagent findings} + +### Established Patterns +{Patterns that constrain/enable this phase} + +### Integration Points +{Where new code connects to existing system} + + + +## Specific Ideas + +{Any particular references from corrections or user input} + +[If none: "No specific requirements — open to standard approaches"] + + + +## Deferred Ideas + +{Ideas mentioned during corrections that are out of scope} + +### Reviewed Todos (not folded) +{Todos reviewed but not folded — with reason} + +[If none: "None — analysis stayed within phase scope"] + +``` + +Write file. + + + +Write audit trail of assumptions and corrections. + +**File:** `${phase_dir}/${padded_phase}-DISCUSSION-LOG.md` + +```markdown +# Phase {PHASE}: {phase_name} - Discussion Log (Assumptions Mode) + +> **Audit trail only.** Do not use as input to planning, research, or execution agents. +> Decisions captured in CONTEXT.md — this log preserves the analysis. + +**Date:** {ISO date} +**Phase:** {padded_phase}-{phase_name} +**Mode:** assumptions +**Areas analyzed:** {comma-separated area names} + +## Assumptions Presented + +### {Area Name} +| Assumption | Confidence | Evidence | +|------------|-----------|----------| +| {Statement} | {Confident/Likely/Unclear} | {file paths} | + +{Repeat for each area} + +## Corrections Made + +{If corrections were made:} + +### {Area Name} +- **Original assumption:** {what Claude assumed} +- **User correction:** {what the user chose instead} +- **Reason:** {user's rationale, if provided} + +{If no corrections: "No corrections — all assumptions confirmed."} + +## Auto-Resolved + +{If --auto and Unclear items existed:} +- {Assumption}: auto-selected {recommended option} + +{If not applicable: omit this section} + +## External Research + +{If research was performed:} +- {Topic}: {Finding} (Source: {URL}) + +{If no research: omit this section} +``` + +Write file. + + + +Commit phase context and discussion log: + +```bash +node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" commit "docs(${padded_phase}): capture phase context (assumptions mode)" --files "${phase_dir}/${padded_phase}-CONTEXT.md" "${phase_dir}/${padded_phase}-DISCUSSION-LOG.md" +``` + +Confirm: "Committed: docs(${padded_phase}): capture phase context (assumptions mode)" + + + +Update STATE.md with session info: + +```bash +node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" state record-session \ + --stopped-at "Phase ${PHASE} context gathered (assumptions mode)" \ + --resume-file "${phase_dir}/${padded_phase}-CONTEXT.md" +``` + +Commit STATE.md: + +```bash +node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" commit "docs(state): record phase ${PHASE} context session" --files .planning/STATE.md +``` + + + +Present summary and next steps: + +``` +Created: .planning/phases/${PADDED_PHASE}-${SLUG}/${PADDED_PHASE}-CONTEXT.md + +## Decisions Captured (Assumptions Mode) + +### {Area Name} +- {Key decision} (from assumption / corrected) + +{Repeat per area} + +[If corrections were made:] +## Corrections Applied +- {Area}: {original} → {corrected} + +[If deferred ideas exist:] +## Noted for Later +- {Deferred idea} — future phase + +--- + +## ▶ Next Up + +**Phase ${PHASE}: {phase_name}** — {Goal from ROADMAP.md} + +`/gsd:plan-phase ${PHASE}` + +`/clear` first → fresh context window + +--- + +**Also available:** +- `/gsd:plan-phase ${PHASE} --skip-research` — plan without research +- `/gsd:ui-phase ${PHASE}` — generate UI design contract (if frontend work) +- Review/edit CONTEXT.md before continuing + +--- +``` + + + +Check for auto-advance trigger: + +1. Parse `--auto` flag from $ARGUMENTS +2. Sync chain flag: + ```bash + if [[ ! "$ARGUMENTS" =~ --auto ]]; then + node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-set workflow._auto_chain_active false 2>/dev/null + fi + ``` +3. Read chain flag and user preference: + ```bash + AUTO_CHAIN=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-get workflow._auto_chain_active 2>/dev/null || echo "false") + AUTO_CFG=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-get workflow.auto_advance 2>/dev/null || echo "false") + ``` + +**If `--auto` flag present AND `AUTO_CHAIN` is not true:** +```bash +node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-set workflow._auto_chain_active true +``` + +**If `--auto` flag present OR `AUTO_CHAIN` is true OR `AUTO_CFG` is true:** + +Display banner: +``` +━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ + GSD ► AUTO-ADVANCING TO PLAN +━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ + +Context captured (assumptions mode). Launching plan-phase... +``` + +Launch: `Skill(skill="gsd:plan-phase", args="${PHASE} --auto")` + +Handle return: PHASE COMPLETE / PLANNING COMPLETE / INCONCLUSIVE / GAPS FOUND +(identical handling to discuss-phase.md auto_advance step) + +**If neither `--auto` nor config enabled:** +Route to confirm_creation step. + + + + + +- Phase validated against roadmap +- Prior context loaded (no re-asking decided questions) +- Codebase deeply analyzed via Explore subagent (5-15 files read) +- Assumptions surfaced with evidence and confidence levels +- User confirmed or corrected assumptions (~2-4 interactions max) +- Scope creep redirected to deferred ideas +- CONTEXT.md captures actual decisions (identical format to discuss mode) +- CONTEXT.md includes canonical_refs with full file paths (MANDATORY) +- CONTEXT.md includes code_context from codebase analysis +- DISCUSSION-LOG.md records assumptions and corrections as audit trail +- STATE.md updated with session info +- User knows next steps + diff --git a/get-shit-done/workflows/plan-phase.md b/get-shit-done/workflows/plan-phase.md index a8de7b37..f30140e5 100644 --- a/get-shit-done/workflows/plan-phase.md +++ b/get-shit-done/workflows/plan-phase.md @@ -187,11 +187,19 @@ If `context_path` is not null, display: `Using phase context from: ${context_pat **If `context_path` is null (no CONTEXT.md exists):** +Read discuss mode for context gate label: +```bash +DISCUSS_MODE=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-get workflow.discuss_mode 2>/dev/null || echo "discuss") +``` + Use AskUserQuestion: - header: "No context" - question: "No CONTEXT.md found for Phase {X}. Plans will use research and requirements only — your design preferences won't be included. Continue or capture context first?" - options: - "Continue without context" — Plan using research + requirements only + If `DISCUSS_MODE` is `"assumptions"`: + - "Gather context (assumptions mode)" — Analyze codebase and surface assumptions before planning + If `DISCUSS_MODE` is `"discuss"` (or unset): - "Run discuss-phase first" — Capture design decisions before planning If "Continue without context": Proceed to step 5. diff --git a/get-shit-done/workflows/progress.md b/get-shit-done/workflows/progress.md index c0ba54a6..58b7a8ca 100644 --- a/get-shit-done/workflows/progress.md +++ b/get-shit-done/workflows/progress.md @@ -18,6 +18,10 @@ if [[ "$INIT" == @file:* ]]; then INIT=$(cat "${INIT#@file:}"); fi Extract from init JSON: `project_exists`, `roadmap_exists`, `state_exists`, `phases`, `current_phase`, `next_phase`, `milestone_version`, `completed_count`, `phase_count`, `paused_at`, `state_path`, `roadmap_path`, `project_path`, `config_path`. +```bash +DISCUSS_MODE=$(node "$HOME/.claude/get-shit-done/bin/gsd-tools.cjs" config-get workflow.discuss_mode 2>/dev/null || echo "discuss") +``` + If `project_exists` is false (no `.planning/` directory): ``` @@ -99,6 +103,7 @@ Present: **Progress:** {PROGRESS_BAR} **Profile:** [quality/balanced/budget/inherit] +**Discuss mode:** {DISCUSS_MODE} ## Recent Work - [Phase X, Plan Y]: [what was accomplished - 1 line from summary-extract] diff --git a/tests/copilot-install.test.cjs b/tests/copilot-install.test.cjs index 297a9404..ad8185ea 100644 --- a/tests/copilot-install.test.cjs +++ b/tests/copilot-install.test.cjs @@ -746,10 +746,10 @@ describe('Copilot agent conversion - real files', () => { assert.ok(toolsLine.includes("'read'"), 'Read mapped'); }); - test('all 17 agents convert without error', () => { + test('all 18 agents convert without error', () => { const agents = fs.readdirSync(agentsSrc) .filter(f => f.startsWith('gsd-') && f.endsWith('.md')); - assert.strictEqual(agents.length, 17, `expected 17 agents, got ${agents.length}`); + assert.strictEqual(agents.length, 18, `expected 18 agents, got ${agents.length}`); for (const agentFile of agents) { const content = fs.readFileSync(path.join(agentsSrc, agentFile), 'utf8'); @@ -1120,7 +1120,7 @@ const crypto = require('crypto'); const INSTALL_PATH = path.join(__dirname, '..', 'bin', 'install.js'); const EXPECTED_SKILLS = 53; -const EXPECTED_AGENTS = 17; +const EXPECTED_AGENTS = 18; function runCopilotInstall(cwd) { const env = { ...process.env }; @@ -1189,6 +1189,7 @@ describe('E2E: Copilot full install verification', () => { const gsdAgents = files.filter(f => f.startsWith('gsd-') && f.endsWith('.agent.md')).sort(); const expected = [ 'gsd-advisor-researcher.agent.md', + 'gsd-assumptions-analyzer.agent.md', 'gsd-codebase-mapper.agent.md', 'gsd-debugger.agent.md', 'gsd-executor.agent.md', diff --git a/tests/discuss-mode.test.cjs b/tests/discuss-mode.test.cjs new file mode 100644 index 00000000..97d2e3de --- /dev/null +++ b/tests/discuss-mode.test.cjs @@ -0,0 +1,101 @@ +/** + * Discuss Mode Config Tests + * + * Validates workflow.discuss_mode config, routing, and assumptions workflow integration. + */ + +const { test, describe } = require('node:test'); +const assert = require('node:assert'); +const fs = require('fs'); +const path = require('path'); + +describe('workflow.discuss_mode config', () => { + test('config template includes discuss_mode default', () => { + const template = JSON.parse( + fs.readFileSync(path.join(__dirname, '..', 'get-shit-done', 'templates', 'config.json'), 'utf8') + ); + assert.strictEqual(template.workflow.discuss_mode, 'discuss'); + }); + + test('discuss-phase command references both workflow files', () => { + const command = fs.readFileSync( + path.join(__dirname, '..', 'commands', 'gsd', 'discuss-phase.md'), 'utf8' + ); + assert.ok(command.includes('discuss-phase-assumptions.md'), 'should reference assumptions workflow'); + assert.ok(command.includes('discuss-phase.md'), 'should reference discuss workflow'); + assert.ok(command.includes('workflow.discuss_mode'), 'should reference config key'); + }); + + test('discuss-phase command argument-hint includes --text', () => { + const command = fs.readFileSync( + path.join(__dirname, '..', 'commands', 'gsd', 'discuss-phase.md'), 'utf8' + ); + assert.ok(command.includes('--text'), 'argument-hint should include --text'); + }); + + test('assumptions workflow file exists and has required steps', () => { + const workflow = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'discuss-phase-assumptions.md'), 'utf8' + ); + const requiredSteps = [ + 'initialize', 'check_existing', 'load_prior_context', + 'deep_codebase_analysis', 'present_assumptions', 'correct_assumptions', + 'write_context', 'write_discussion_log', 'auto_advance' + ]; + for (const step of requiredSteps) { + assert.ok(workflow.includes(` { + const workflow = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'discuss-phase-assumptions.md'), 'utf8' + ); + const sections = ['', '', '', '', '', '']; + for (const section of sections) { + assert.ok(workflow.includes(section), `missing CONTEXT.md section: ${section}`); + } + }); + + test('plan-phase gate references discuss_mode config', () => { + const planPhase = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'plan-phase.md'), 'utf8' + ); + assert.ok(planPhase.includes('workflow.discuss_mode'), 'should reference config key'); + assert.ok(planPhase.includes('assumptions mode'), 'should mention assumptions mode'); + }); + + test('assumptions workflow handles --auto flag', () => { + const workflow = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'discuss-phase-assumptions.md'), 'utf8' + ); + assert.ok(workflow.includes('--auto'), 'should handle --auto'); + assert.ok(workflow.includes('auto-select'), 'should auto-select in --auto mode'); + assert.ok(workflow.includes('auto_advance'), 'should support auto_advance'); + }); + + test('assumptions workflow handles --text flag', () => { + const workflow = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'discuss-phase-assumptions.md'), 'utf8' + ); + assert.ok(workflow.includes('text_mode'), 'should reference text_mode config'); + assert.ok(workflow.includes('--text'), 'should handle --text flag'); + }); + + test('progress workflow references discuss_mode', () => { + const progress = fs.readFileSync( + path.join(__dirname, '..', 'get-shit-done', 'workflows', 'progress.md'), 'utf8' + ); + assert.ok(progress.includes('workflow.discuss_mode'), 'should read discuss_mode config'); + assert.ok(progress.includes('Discuss mode'), 'should display discuss mode'); + }); + + test('documentation file exists', () => { + const docPath = path.join(__dirname, '..', 'docs', 'workflow-discuss-mode.md'); + assert.ok(fs.existsSync(docPath), 'docs/workflow-discuss-mode.md should exist'); + const doc = fs.readFileSync(docPath, 'utf8'); + assert.ok(doc.includes('assumptions'), 'doc should mention assumptions'); + assert.ok(doc.includes('discuss'), 'doc should mention discuss'); + assert.ok(doc.includes('config-set'), 'doc should show how to configure'); + }); +});