April 5, 2014

...Learn TDD with Codemanship

Why It's Better To Start With A Test

The art of Test-driven Development is, at its essence, the art of generalising from a set of examples to discover the patterns that bind them.

The TDD practice of triangulation, where we flesh out the design of our code one test case at a time, generalising as we go, has its analogues in other software specification practices.

For example, in the Catalysis approach to model-driven development, practitioners use object diagrams to illustrate the before and after of actions, and generalise from this to static models like class diagrams.

In user experience design, it's recommended to start with examples of the kinds of users who'll be working with our software and the tasks they'll be performing.

Going back to Ivar Jacobson's "usage cases" in the late 1960's, and probably beyond to the 1950's when enlightened teams used tests to drive their implementations, the received wisdom has been to start with examples and work our way back to a general solution that will satisfy all of them.

When we do it the other way around - e.g., we create object diagrams based on our class model to illustrate specific examples - that's what we call "testing" or "verification" (or "validation", if our goal is to validate that our speciffication really describes what the users need).

With good reason, we frown on starting with generalised designs and then comig up with examples afterwards. Firstly, what are our generalised designs based on? How did we know we needed an X or a Y in our design?

Psychologically, the effect of the order in which we do it - examples first, and the generalise, or generalise first and then test with examples - can be quite profound.

In Codemanship training courses, there'll often be one or two pairs in the group when we do the OO design exercise who skip agreeing acceptance tests* and go straight for a design. They call me over and ask "Is this the right design?" and I say "I don't know; will it pass your acceptance test?" and they look sheepishly back at me and say "Ah, we didn't agree a test". What follows is usually an attempt to agree an acceptance test that doesn't invalidate their design.

We can grow rapidly - almost instantly - attached to our solutions. So much so that I see teams actively avoiding any feedback that might invalidate them. Knowing this, I therefore very strongly recommend that teams start with the examples and work directly towards a simple design that they can be confident will work for all of those scenarios.

For sure, they still grow attached to their designs, but by starting with the test cases, there's far less danger thast the designs they grow attached to will fail to give users what they need.

* Yes, even on a course called "Test-driven Development"

Posted 6 years, 8 months ago on April 5, 2014