Should All Code Be Written With TDD?


As I have mentioned many times before, Test-Driven Development (TDD) is a handy technique for engineering low-complexity computer code. And low complexity in our programming is vital if we want to maintain software over years and even decades.

However, it’s worth asking the question of whether TDD is appropriate in all situations. The same goes for unit testing in general—under what circumstances will unit tests deliver little value?

Hmm, I suppose this would be program behaviour that we do not care a great deal for—code that may be present but can also be absent at times, and we are not concerned for its exact form.

Diagnostic Logging

Let’s use the example used in my article on separating implementation and diagnostic code:

AccountProvider.GetAccount() is implemented as

  public virtual async Task<Account> GetAccount(string accountNumber)
     return await Reader.GetAccount(accountNumber);       

As programmers, we want to log how we are calling Reader.GetAccount() and also what the call returned. Rather than litter this code with distracting log statements, we’ll add the logging into a separate LoggedAccountProvider class that overrides the GetAccount() method and contains the log statements:

  public override async Task<Account> GetAccount(string accountNumber)
     await Logger.LogDebug($"Call AccountProvider.GetAccount('{accountNumber}').");
     var account = await base.GetAccount(accountNumber);
     var result = account != null ? $"a '{account.BankName}' account" : "null";
     await Logger.LogDebug($"AccountProvider.GetAccount('{accountNumber}') returned {result}.");
     return account;

LoggedAccountProvider.GetAccount() invokes the base functionality of AccountProvider.GetAccount(), via the call to base.GetAccount(). It also logs this call—pre and post. 

Now, as developers, we may not be too fussed, and readily change our minds about how we do the logging—maybe we only want the pre-call or post-call logging. Or we have changed our minds about the specific logging messages and log levels. Assuming we are that ambivalent about our logging, is it necessary to have unit tests or use TDD to write the logging code?  

No, probably not. 

In the past, I used TDD to specify the log statements. However, I usually discovered that writing tests for log statements didn’t add a lot of value. I often had to modify unit tests simply because I wanted to change the log messages—this felt like make-work. 

TDD and unit tests are more helpful in verifying required program behaviour than optional functionality, i.e. logging.

0 replies

Leave a Reply

Want to join the discussion?
Feel free to contribute!

Leave a Reply