/tdd-workflow
TDD London School workflow -- mock-first, outside-in test development
Claude Code
$ npx -y skills add ruvnet/ruflo --skill tdd-workflow --agent claude-code
Codex
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a codex -y
Cursor
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a cursor -y
Gemini CLI
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a gemini-cli -y
GitHub Copilot
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a github-copilot -y
OpenCode
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a opencode -y
Windsurf
$ npx skills add ruvnet/ruflo --skill tdd-workflow -a windsurf -y
SKILL.md
tdd-workflow.SKILL.mdname: tdd-workflow
description: TDD London School workflow -- mock-first, outside-in test development
argument-hint: "<module-path>"
allowed-tools: Bash(npx * npm *) mcp__plugin_ruflo-core_ruflo__hooks_pre-task mcp__plugin_ruflo-core_ruflo__hooks_post-task Read Write Edit
Follow the TDD London School (mock-first) approach:
1. **Write the failing test first** -- define expected behavior with mocked dependencies 2. **Run the test** -- confirm it fails for the right reason 3. **Implement minimal code** -- make the test pass with the simplest solution 4. **Refactor** -- clean up while keeping tests green 5. **Repeat** -- add the next behavior
Before starting: `mcp__plugin_ruflo-core_ruflo__hooks_pre-task({ description: "TDD: FEATURE_NAME" })` Before reporting the outcome, run the final target tests and the regression suite after the last edit. Record the actual commands, exit codes, whether tests ran, and failing test names. The initial red test is expected during TDD; only the final validation determines success.
Call `mcp__plugin_ruflo-core_ruflo__hooks_post-task` with the observed result, including when the task is abandoned or validation is interrupted. Set `completed`, `targetTestsRan`, and `regressionTestsRan` to true only when observed; use null for missing exit codes. Skipped or unrun validation is not success. Never substitute an expected result for an observed one.
The following example maps those observations to the hook input (tool-call notation):
const success = completed && targetTestsRan && regressionTestsRan
&& targetExitCode === 0 && regressionExitCode === 0;
mcp__plugin_ruflo-core_ruflo__hooks_post-task({
taskId: "tdd-FEATURE",
success,
storeResults: true,
task: JSON.stringify({
feature: "FEATURE",
targetCommand, targetExitCode, targetTestsRan,
regressionCommand, regressionExitCode, regressionTestsRan,
failingTestNames,
failureReason: success ? null : failureReason
})
});On failure, report `success: false` and the failing test names in `task`. If the runner failed before identifying tests, or the task was abandoned, state that reason instead of inventing test names.
Principles:
- Mock external dependencies at boundaries
- Test behavior, not implementation
- One assertion per test when possible
- Descriptive names: `should [behavior] when [condition]`
Read more
name: tdd-workflow description: TDD London School workflow -- mock-first, outside-in test development argument-hint: "<module-path>" allowed-tools: Bash(npx * npm *) mcp__plugin_ruflo-core_ruflo__hooks_pre-task mcp__plugin_ruflo-core_ruflo__hooks_post-task Read Write Edit
Follow the TDD London School (mock-first) approach:
1. **Write the failing test first** -- define expected behavior with mocked dependencies 2. **Run the test** -- confirm it fails for the right reason 3. **Implement minimal code** -- make the test pass with the simplest solution 4. **Refactor** -- clean up while keeping tests green 5. **Repeat** -- add the next behavior
Before starting: `mcp__plugin_ruflo-core_ruflo__hooks_pre-task({ description: "TDD: FEATURE_NAME" })` Before reporting the outcome, run the final target tests and the regression suite after the last edit. Record the actual commands, exit codes, whether tests ran, and failing test names. The initial red test is expected during TDD; only the final validation determines success.
Call `mcp__plugin_ruflo-core_ruflo__hooks_post-task` with the observed result, including when the task is abandoned or validation is interrupted. Set `completed`, `targetTestsRan`, and `regressionTestsRan` to true only when observed; use null for missing exit codes. Skipped or unrun validation is not success. Never substitute an expected result for an observed one.
The following example maps those observations to the hook input (tool-call notation):
const success = completed && targetTestsRan && regressionTestsRan
&& targetExitCode === 0 && regressionExitCode === 0;
mcp__plugin_ruflo-core_ruflo__hooks_post-task({
taskId: "tdd-FEATURE",
success,
storeResults: true,
task: JSON.stringify({
feature: "FEATURE",
targetCommand, targetExitCode, targetTestsRan,
regressionCommand, regressionExitCode, regressionTestsRan,
failingTestNames,
failureReason: success ? null : failureReason
})
});On failure, report `success: false` and the failing test names in `task`. If the runner failed before identifying tests, or the task was abandoned, state that reason instead of inventing test names.
Principles:
- Mock external dependencies at boundaries
- Test behavior, not implementation
- One assertion per test when possible
- Descriptive names: `should [behavior] when [condition]`
📖 RuFlo Explained — Build an AI Team That Plans, Remembers, Tests, and Improves A 14-chapter guide: from the basic idea to a first useful task, then memory, agent teams, plugins, cost and verification. Agent = Model + Harness.
Other skills on ruflo.
More skills from other plugins.
agentmail
Use your assigned AgentMail inbox to read email tasks, explicitly send or reply, and check delivery. Provided automatically by…
bmad
Answers BMad questions and recommends the next skill from what is installed. Use when the user asks bmad for help, what to do…
Questions about tdd-workflow.
- Which coding agents can use tdd-workflow?
- tdd-workflow installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.

