Claude
Skills
Sign in
โ† Back

tdd-workflow

Included with Lifetime
$97 forever

Strict TDD state machine with Result types. 7-state workflow (PLANNING, RED, GREEN, REFACTOR, VERIFY, BLOCKED, VIOLATION). Every message MUST announce state. Integrates with fn(args, deps), vitest-mock-extended, and typed error handling.

Code Review

What this skill does


# TDD Workflow

Strict test-driven development with Result types, dependency injection, and state machine governance.

## The Iron Law

```
NO PRODUCTION CODE WITHOUT A FAILING TEST FIRST
```

Write code before the test? **Delete it. Start over.**

**No exceptions:**
- Don't keep it as "reference"
- Don't "adapt" it while writing tests
- Don't look at it
- Delete means delete

Implement fresh from tests. Period.

**Rationale:** Code written before tests is biased by implementation. TDD requires tests to drive design, not verify existing code.

## CRITICAL: STATE MACHINE GOVERNANCE

**EVERY SINGLE MESSAGE MUST START WITH YOUR CURRENT TDD STATE**

Format:
```
โšช TDD: PLANNING
๐Ÿ”ด TDD: RED
๐ŸŸข TDD: GREEN
๐Ÿ”ต TDD: REFACTOR
๐ŸŸก TDD: VERIFY
โš ๏ธ TDD: BLOCKED
๐Ÿ”ฅ TDD: VIOLATION
```

**NOT JUST THE FIRST MESSAGE. EVERY. SINGLE. MESSAGE.**

When you read a file โ†’ prefix with TDD state
When you run tests โ†’ prefix with TDD state
When you explain results โ†’ prefix with TDD state
When you ask a question โ†’ prefix with TDD state

Example:
```
โšช TDD: PLANNING
Writing test for getUser returning NOT_FOUND...

โšช TDD: PLANNING
Running npm test to see it fail...

๐Ÿ”ด TDD: RED
Test fails correctly. Implementing minimum solution...

๐ŸŸข TDD: GREEN
Test passes. Checking if refactor needed...
```

## State Machine Diagram

```
                  user request
                       โ†“
                 โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
            โ”Œโ”€โ”€โ”€โ”€โ”‚ PLANNING โ”‚โ”€โ”€โ”€โ”€โ”
            โ”‚    โ””โ”€โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”˜    โ”‚
            โ”‚          โ”‚         โ”‚
            โ”‚  test fails        โ”‚
            โ”‚  correctly         โ”‚
  unclear   โ”‚          โ†“         โ”‚ blocker
            โ”‚    โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”    โ”‚
            โ””โ”€โ”€โ”€โ”€โ”‚   RED    โ”‚    โ”‚
                 โ”‚          โ”‚    โ”‚
                 โ”‚ Test IS  โ”‚    โ”‚
                 โ”‚ failing  โ”‚    โ”‚
                 โ””โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”˜    โ”‚
                      โ”‚          โ”‚
              test    โ”‚          โ”‚
              passes  โ”‚          โ”‚
                      โ†“          โ”‚
                 โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”    โ”‚
                 โ”‚  GREEN   โ”‚    โ”‚
                 โ”‚          โ”‚    โ”‚
                 โ”‚ Test IS  โ”‚    โ”‚
                 โ”‚ passing  โ”‚    โ”‚
                 โ””โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”˜โ”€โ”€โ”€โ”€โ”˜
                      โ”‚
          refactoring โ”‚
          needed      โ”‚
                      โ†“
                 โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
            โ”Œโ”€โ”€โ”€โ”€โ”‚ REFACTOR โ”‚
            โ”‚    โ”‚          โ”‚
            โ”‚    โ”‚ Improve  โ”‚
            โ”‚    โ”‚ design   โ”‚
            โ”‚    โ””โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”˜
            โ”‚         โ”‚
            โ”‚    done โ”‚
            โ”‚         โ”‚
            โ”‚         โ†“
            โ”‚    โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
            โ”‚    โ”‚  VERIFY  โ”‚
            โ”‚    โ”‚          โ”‚
            โ”‚    โ”‚ Run full โ”‚
  fail      โ”‚    โ”‚ suite +  โ”‚
            โ”‚    โ”‚ lint +   โ”‚
            โ””โ”€โ”€โ”€โ”€โ”‚ build    โ”‚
                 โ””โ”€โ”€โ”€โ”€โ”ฌโ”€โ”€โ”€โ”€โ”€โ”˜
                      โ”‚
                 pass โ”‚
                      โ”‚
                      โ†“
                 [COMPLETE]
```

## State: PLANNING

**Prefix:** `โšช TDD: PLANNING`

**Purpose:** Write a failing test that proves the requirement.

### Pre-Conditions
- User has provided a task/requirement/bug report
- No other TDD cycle in progress

### The Delete Rule

If production code exists before the test:
1. **Delete it immediately**
2. Do not keep as "reference"
3. Do not "adapt" it
4. Start fresh from the test

**Rationale:** Code written before tests is biased by implementation. TDD requires tests to drive design, not verify existing code.

### Actions
1. Analyze requirement - what behavior needs testing?
2. Identify edge cases
3. Write test using fn(args, deps) pattern
4. Use vitest-mock-extended: `const deps = mock<GetUserDeps>()`
5. Run test (use Bash tool)
6. **VERIFY test fails correctly** (MANDATORY - see Verify RED below)
7. Show exact failure message verbatim
8. Justify why failure proves test is correct

### Verify RED - Watch It Fail

**MANDATORY. Never skip.**

```bash
npm test path/to/test.test.ts
```

Confirm:
- Test fails (not errors)
- Failure message is expected
- Fails because feature missing (not typos)

**Test passes?** You're testing existing behavior. Fix test.
**Test errors?** Fix error, re-run until it fails correctly.

### Post-Conditions (ALL required before transition)
- [ ] Test written with proper deps mocking
- [ ] Test executed
- [ ] Test FAILED correctly (not setup error) - **VERIFIED by watching it fail**
- [ ] Failure message shown verbatim
- [ ] Failure is "meaningful" (assertion failure, not import error)

### Validation Before Transition
```
Pre-transition validation:
โœ“ Test written: [yes/no]
โœ“ Test executed: [yes/no]
โœ“ Test failed correctly: [yes - output above]
โœ“ Meaningful failure: [yes - justification]

Transitioning to RED.
```

### Transitions
- PLANNING โ†’ RED (test fails correctly)
- PLANNING โ†’ BLOCKED (cannot write valid test)

## State: RED

**Prefix:** `๐Ÿ”ด TDD: RED`

**Purpose:** Test IS failing. Implement ONLY what the error message demands.

### Pre-Conditions
- Test written and executed
- Test IS FAILING correctly
- Failure is meaningful (not setup/syntax error)

### The Hardcode Rule

Before implementing, announce:
```
Minimal implementation check:
- Error demands: [what the error literally says]
- Could hardcoded value work? [yes/no]
- If yes: [what hardcoded value]
- If no: [why real logic is required]
```

| Error Says | Do This |
|-----------|---------|
| `expected err('NOT_FOUND')` | `return err('NOT_FOUND')` |
| `expected ok(user)` | `return ok(mockUser)` |
| `expected count: 0` | `return { count: 0 }` |

Only add logic when tests FORCE you to.

### Actions
1. Read error message - what does it literally ask for?
2. Announce minimal implementation check
3. Implement ONLY what error demands (hardcode if possible)
4. Run test
5. **VERIFY test PASSES** (MANDATORY - see Verify GREEN below)
6. Run typecheck (`npm run typecheck`)
7. Run lint (`npm run lint`)
8. Show all output verbatim
9. Transition to GREEN

### Verify GREEN - Watch It Pass

**MANDATORY. Never skip.**

```bash
npm test path/to/test.test.ts
```

Confirm:
- Test passes
- Other tests still pass
- Output pristine (no errors, warnings)

**Test fails?** Fix code, not test.
**Other tests fail?** Fix now.

### Post-Conditions (ALL required)
- [ ] Implemented ONLY what error demanded
- [ ] Test executed and PASSES
- [ ] Code compiles (no TypeScript errors)
- [ ] Code lints (no ESLint errors)
- [ ] All output shown verbatim

### Validation Before Transition
```
Post-condition validation:
โœ“ Test PASSES: [yes - output above]
โœ“ Code compiles: [yes - output above]
โœ“ Code lints: [yes - output above]
โœ“ Implementation minimal: [justification]

Transitioning to GREEN.
```

### Critical Rules
- NEVER transition to GREEN without test PASS + compile + lint
- NEVER anticipate future errors - address THIS error only
- NEVER change test to match implementation - fix the code

### Transitions
- RED โ†’ GREEN (test passes, code compiles, code lints)
- RED โ†’ BLOCKED (cannot make test pass)
- RED โ†’ PLANNING (test failure reveals misunderstood requirement)

## State: GREEN

**Prefix:** `๐ŸŸข TDD: GREEN`

**Purpose:** Test IS passing. Assess code quality and decide next step.

### Pre-Conditions
- Test exists and PASSES
- Code compiles and lints
- Implementation is minimal

### Actions
1. Review implementation against patterns:

| Pattern | Check |
|---------|-------|
| fn(args, deps) | Is deps type explicit and minimal? |
| Result types | Are all error cases typed? |
| Validation | Is Zod at boundary only? |
| Naming | Domain-specific, not generic? |

2. Decide: Does code need refactoring?
3. If YES โ†’ REFACTOR
4. If NO โ†’ VERIFY

### Post-Conditions
- [ ] Test IS PASSING
- [ ] Code quality assessed
- [ ] Decision made: refactor or verify

### Transitions
- GREEN โ†’ REFACTOR (improvements needed)
- GREEN โ†’ VERIFY (code is clean)
- GREEN โ†’ RED (test starts failing - regression)

## State: REFACTOR

**Prefix:** `๐Ÿ”ต TDD: REFACTOR`

**Purpose:** Tests ARE passing. Improve design while keeping green.

### Pre-Conditions
- Tests ARE 

Related in Code Review