The important thing is that I am trying to do TDD by first writing down all my tests, and then writing the code.
The problem is that “writing all my tests first” most categorically doesn't “do [some] TDD”. Test-based development consists of many small repetitions of the red-green-refactor cycle:
- Add unit test to the test suite, run it and see how it worked (red)
- Add enough code to the system under test to run all pass tests (green)
- Improve the design of the system under test (usually by removing duplication), while maintaining all the tests (refactoring)
If you program the entire huge set of tests, you will always try to get to the green state (all tests).
However, the application will not compile because none of my objects or methods exist.
This is typical of any compiled language; This is not a TDD problem per se. All this means that in order to see how the new test failed, you may have to write a minimal stub for any function that you are currently working on to make the compiler happy.
For example, I can write this test (using NUnit):
[Test] public void DefaultGreetingIsHelloWorld() { WorldGreeter target = new WorldGreeter(); string expected = "Hello, world!"; string actual = target.Greet(); Assert.AreEqual(expected, actual); }
And I would have to write this a lot of code to get the application to compile, and the test failed:
public class WorldGreeter { public string Greet() { return String.Empty; } }
Once I got the build solution, and I saw one failed test, I can add code to make the first test pass:
public string Greet() { return "Hello, world!"; }
Once all the tests have passed, I will be able to review the system under test and see what can be done to improve the design. However, it is important that the TDD discipline go through both the red and green steps before playing with refactoring.
I thought that the whole point is that when developing tests, you can start viewing duplicates, etc., so that you can reorganize before writing one line of code.
Martin Fowler defines refactoring as “a disciplined technique for restructuring existing code, changing its internal structure without changing its external behavior ” (emphasis added). If you haven't written a single line of code, you have nothing to reorganize.
So the question is, is there a way to do this, or am I doing it wrong?
If you want to do TDD, then yes, I'm afraid you are doing it wrong. You can very well deliver excellent code by doing what you do, but this is not TDD; regardless of whether there is a problem for you to decide.