TEST-DRIVEN DEVELOPMENT: RED, GREEN, REFACTOR
In their book The Art of Agile Development, Shore and Warden describe Test-Driven Development (TDD) as "a small, fast-spinning motor. It operates in a very short cycle that repeats over and over again. Every few minutes. this cycle ratchets your code forward a notch, providing code that—although it may not be finished—has been tested, designed, coded and is ready to check in."
TDD is a discipline for writing code, writing developer (unit) tests, and doing design work in an integrated approach. A useful mnemonic for remembering the basic TDD cycle is "red > green > refactor." Here is a short summary of each of the steps.
RED: Start by thinking of a behavior you want the software to have which could be implemented by a few lines of code (fewer than five is a good target). Then write a test (also only a few lines of code) that will fail unless that behavior is present. Focus on:
The class behavior and its public interface - not how to implement the internals of the class.
The class user, not the class implementer - you may need to write the first few tests with class and method names that do not yet exist. Run the test suite, and watch the new test should fail. If the test either does not fail or fails in a different way than you intended, make the necessary fixes.
GREEN: Write just enough code to get the test to pass. Focus on:
Getting something to work
Simplest possible implementation, rather than the most elegant solution (even hard-coded values are okay).
Reverting to known good code is the test continues to fail
If after a few attempts you can't make the test pass, consider starting over with a different test, possibly employing even less code. You are done with this step when the test passes.
REFACTOR:Now that the code does what you want, use refactoring to make the design right. Focus on:
Making the code readable and eliminating duplication
Existing behavior (refactoring means changing the code without changing its behavior; adding new behavior requires writing a new [failing] test).
Working in small steps, running the tests each time.
The cycle then repeats with each new behavior you want to have. The entire cycle should take between 5-10 minutes.
A couple of last points to emphasize:
Tests are checked in with the rest of the code (they are essentially living documentation of the code)
Tests are run with every build