Overview
Test-Driven Development is the practice of writing a failing test before writing the code that makes it pass, then refactoring under a green bar. Its real payoff is not test coverage but design pressure: code written test-first tends toward small, decoupled, intention- revealing units. Popularized by Kent Beck (Test-Driven Development: By Example).
Key points
- The cycle: red (write a failing test) → green (simplest code that passes) → refactor (improve structure, tests stay green). Small steps, minutes not hours.
- Tests as design feedback: hard-to-write tests signal coupling or unclear responsibilities — listen to the test.
- Schools: Classicist/Detroit (state-based, real collaborators) vs. Mockist/London (interaction-based, outside-in with mocks). Know both, choose per context.
- Triangulation & obvious implementation: strategies for how big a step to take.
- Test behavior, not implementation: tests coupled to internals rot fast and block refactoring — the opposite of the goal.
- TDD ≠ unit tests only: the discipline scales to outside-in loops with acceptance tests (see BDD, the double-loop).
- To explore: property-based testing, mutation testing, TDD with legacy code (characterization tests, Michael Feathers).
Practice
- FizzBuzz kata (source) — the smallest possible red/green/refactor loop; drill the rhythm until writing the test first is reflex.
- String Calculator kata (source) — Osherove's incremental-requirements classic; take one requirement at a time and never code ahead of the tests.
- Bowling Game kata (source) — triangulation in practice, and an awkward test telling you the design is wrong — listen to it.
- Mars Rover kata (source) — big enough to try both schools: classicist state-based, then mockist outside-in, and compare the designs.
- Build Your Own wc (source) — a real CLI tool test-first; TDD sustained across a whole small product, not a toy.
- Event-sourced bank account (exercise) — double-loop TDD on a substantial build, with given-events/when-command/then-events as the test template.
Related
- BDD — the outside-in, behavior-first evolution of the same discipline.
- Refactoring techniques — the third step of the cycle.
- Clean code — the qualities the refactor step drives toward.
- Hexagonal architecture — ports & adapters make test-first design practical at application scale.
- Testing strategies — where TDD's unit tests sit in the wider portfolio.