Speedy Red Car
Picture by hugovk
AttributionShare AlikeSome rights reserved.

A while ago I promised to write a few articles on the art of test-driven development or TDD1. Rather than starting with TDD itself I wanted to start by talking about what happens when you try to write unit tests after you write your code.

This can happen for any number of reasons. A team may want a suite of unit tests with good coverage but may not be willing or experienced enough to either try TDD or make it work. All too frequently a team that isn’t used to writing unit tests, or can’t get it’s collective head around how you can write a test for something that doesn’t exist yet, will usually revert to writing the test afterwards. The result is that unit tests drop down on the priority list and are the first thing to be cut when a project starts slipping.

This isn’t helped by the fact that the very word “test” implies something done after the fact2. I’ve lost track of the number of interviews or conversations I’ve had where, when TDD comes up, I get a knowing look and the question “Did you really write your tests first?” as if it was okay, I was with friends and could admit that I just dive straight in and write the code first. No, I like to write my unit tests first. That’s why it’s called test-driven development.

As I’ve moved around in a couple of different jobs recently though I’ve found myself working on code with few3 unit tests. As a result I’ve picked up a lot of experience in retrofitting unit-tests to existing code. Over the next few weeks I’ll be sharing some of the experiences I’ve had and how I solved some of the problems that came up.

First up: when a unit test isn’t.

– Fintan


1 – And then proceeded to write nothing at all for the next few months…
2 – Behaviour-Driven Development aims to fix this but more about that in a later article.
3 – If any.



3 Responses to “Retrofitting Unit Tests”  

  1. Hi Fintan,

    I look forward to reading the followup articles.

    Martin Fowler’s book ‘Working Effectively with Legacy Code’ is a wonderful resource for those working with test-challenged code. Retrofitting tests to test-free code can be surprisingly difficult. Code that hasn’t been written with testing in mind usually lacks the seams necessary for effective testing while also having lots of dependencies that make it difficult to set the stage for tests. Fowler’s book is chock full of practical advice for taming test resistant code.

  2. Hi Tony,

    Thanks for the comment. As I’ve been writing these articles I’ve found that there’s certainly enough in the subject to fill a book. I’ll have to pick up Fowler’s book. Thanks for the tip!

    – Fintan

  3. 3 torgeirhelgevold

    The main point is that the code is designed with testability in mind. I am not sure that I want to go so far as to mandate that the test has to be written first. I typically do a combination of writing tests during and right after I have created a piece of code. In large code projects, the compile time overhead may be too large to practice test driven development according to a strict definition.

    As far as legacy code is concerned, one issue that always comes up is data/context dependency. A very typical example of this from Asp.Net is Singeltons that are not defined outside of your web context.
    I usually try to work around this by abstracting the dependencies. My most common approach is to abstract dependencies into virtual methods that I override in my tests.


Leave a Reply