TDD Cycle Skill
Run a full RED-GREEN-REFACTOR Test-Driven Development workflow for a feature. This skill drives the entire TDD lifecycle: understand the feature, write failing tests, confirm they fail (RED), implement minimal code to make them pass (GREEN), then refactor while keeping tests green (REFACTOR).
CRITICAL: Complete ALL 7 phases. The workflow is not complete until Phase 7: Report is finished. After completing each phase, immediately proceed to the next phase without waiting for user prompts.
Core Principles
- Tests before implementation -- Write tests first. The tests define what the code should do. Implementation follows from tests, not the other way around.
- Minimal implementation -- Write only the code needed to make failing tests pass. No extra features, no premature optimization, no speculative abstractions.
- Regression protection -- Existing tests must continue passing at every phase. Zero tolerance for regressions.
- Phase gate enforcement -- Each phase must complete and verify before the next begins. RED verification is mandatory. GREEN verification is mandatory.
- Behavior over implementation -- Tests verify what code does (inputs, outputs, side effects), not how it does it internally.
- Autonomous after plan confirmation -- The user confirms the plan once in Phase 3. After that, the entire RED-GREEN-REFACTOR cycle runs without interruption.
AskUserQuestion is MANDATORY
IMPORTANT: You MUST use the AskUserQuestion tool for ALL questions to the user. Never ask questions through regular text output.
- Plan confirmation -> AskUserQuestion
- Framework selection -> AskUserQuestion
- Clarifying questions -> AskUserQuestion
- Error recovery options -> AskUserQuestion
Text output should only be used for presenting information, summaries, and progress updates.
NEVER do this (asking via text output):
Should I proceed with this plan?
1. Yes
2. No, modify it
ALWAYS do this (using AskUserQuestion tool):
AskUserQuestion:
questions:
- header: "TDD Plan Confirmation"
question: "Review the TDD plan above. Ready to proceed?"
options:
- label: "Proceed"
description: "Run the full RED-GREEN-REFACTOR cycle autonomously"
- label: "Modify plan"
description: "Adjust tests, scope, or approach before starting"
- label: "Cancel"
description: "Cancel the TDD workflow"
multiSelect: false
Phase 1: Parse Input
Goal: Determine the input type and resolve context.
Analyze $ARGUMENTS to determine the operating mode.
Input Type Detection
Feature Description -- triggered when input is:
- Free-text describing a feature (e.g., "add user login with email and password")
- A file path to source code that needs TDD treatment (e.g.,
src/auth/login.py)
Task ID -- triggered when input is:
- A numeric ID, possibly prefixed with
#ortask-(e.g.,5,#5,task-5)
Spec Section -- triggered when input is:
- A spec file path with optional section reference (e.g.,
specs/SPEC-feature.md Section 5.1)
Context Resolution
Feature Description:
- Record the feature description for use in Phase 3 (Plan)
- Use Glob/Grep to find existing related code if a file path is provided
- Determine the target module and directory
Task ID:
- Use
TaskGetto retrieve the full task details - Extract acceptance criteria (Functional, Edge Cases, Error Handling)
- Check
metadata.spec_pathfor the source spec - Record the task's description, requirements, and blocked-by/blocks relationships
Spec Section:
- Read the spec file
- Locate the referenced section
- Extract acceptance criteria, user stories, and edge cases from the section
Error Cases
No input provided:
AskUserQuestion:
questions:
- header: "TDD Input"
question: "What would you like to run TDD for?"
options:
- label: "Feature description"
description: "Describe the feature to build test-first"
- label: "Task ID"
description: "Run TDD for a Claude Code Task"
- label: "Spec section"
description: "Run TDD from a spec's acceptance criteria"
- label: "Retrofit existing code"
description: "Add tests to existing untested code"
multiSelect: false
Then prompt for the specific value based on the selection.
Invalid task ID:
ERROR: Task #{id} not found.
Available tasks:
{List first 5 pending/in-progress tasks from TaskList}
Usage: /tdd-cycle <feature-description|task-id|spec-section>
Invalid spec path:
ERROR: Spec file not found: {path}
Did you mean one of these?
{List matching files from Glob search for similar names}
Usage: /tdd-cycle <spec-path>
Phase 2: Understand
Goal: Load project conventions, detect the test framework, and explore the relevant codebase.
Step 1: Load Project Conventions
Read project-level conventions:
Read: CLAUDE.md
Read: .claude/agent-alchemy.local.md (if it exists)
Load cross-plugin skills for language and project awareness:
Read: ${CLAUDE_PLUGIN_ROOT}/../core-tools/skills/language-patterns/SKILL.md
Read: ${CLAUDE_PLUGIN_ROOT}/../core-tools/skills/project-conventions/SKILL.md
Apply their guidance when writing tests and implementation code.
Step 2: Load TDD Configuration
Read TDD settings from .claude/agent-alchemy.local.md if it exists:
tdd:
framework: auto # auto | pytest | jest | vitest
coverage-threshold: 80 # Minimum coverage percentage (0-100)
strictness: normal # strict | normal | relaxed
test-review-threshold: 70 # Minimum test quality score (0-100)
test-review-on-generate: false # Run test-reviewer after generate-tests
Record the TDD strictness level (default: normal if not configured).
Record the framework override (default: auto -- use detection chain).
Record the coverage threshold (default: 80 -- clamp to 0-100 if out of range).
Error handling:
- If the settings file does not exist, use defaults for all settings.
- If the YAML frontmatter is malformed, use defaults and log a warning.
- If
tdd.frameworkis set to an unrecognized value, fall back to auto-detection.
Step 3: Detect Test Framework
Follow the framework detection chain to identify the project's test framework.
Priority 1 -- Config Files (High Confidence):
Python:
pyproject.tomlwith[tool.pytest.ini_options]or[tool.pytest]-> pytestsetup.cfgwith[tool:pytest]-> pytestpytest.iniexists -> pytestconftest.pyat project root or intests/-> pytest
TypeScript/JavaScript:
vitest.config.*exists -> Vitest (takes priority)jest.config.*exists -> Jestpackage.jsonwithvitestin dependencies/devDependencies -> Vitestpackage.jsonwithjestin dependencies/devDependencies -> Jestpackage.jsonwith"jest": {}config section -> Jest
Priority 2 -- Existing Test Files (Medium Confidence):
test_*.pyor*_test.py-> pytest*.test.ts/*.spec.tswithvitestimports -> Vitest*.test.ts/*.spec.tswithjestimports or no explicit imports -> Jest
Priority 3 -- Settings Fallback (Low Confidence):
- Check
.claude/agent-alchemy.local.mdfortdd.framework
Priority 4 -- User Prompt Fallback:
If all detection methods fail:
AskUserQuestion:
questions:
- header: "Test Framework"
question: "No test framework was detected in this project. Which framework should be used?"
options:
- label: "pytest"
description: "Python testing framework (recommended for Python projects)"
- label: "Jest"
description: "JavaScript/TypeScript testing framework"
- label: "Vitest"
description: "Vite-native testing framework (modern alternative to Jest)"
- label: "Other"
desc