Funding for 'IT Lab' Project, Phase 1: Progress of sticker sales. Purchase a sticker to help us reach our target.Updated: 2010-02-28 11:53
Test Driven Development
Introduction
During my last article I briefly explained what is Test Driven Development is? I thought of doing a separate article about it, because of the value which the TDD can bring in to software development process. Test Driven Development not only a unit testing methodology, rather it is an iterative software development methodology; where you would not write any production code without having a failing test case. As I have explained in my previous article TDD is based on three simple guidelines.
- You may not write production code until you have written a failing unit test
- You may not write more of a unit test than is sufficient to fail, and not compiling is failing.
- You may not write more production code than is sufficient to pass the currently failing test.
These three guide lines explain the iterative process of the TDD.

Golden rule of TDD is never to write production code without having a failing test case. This approach of writing test cases serves many things. Most obvious thing is you can verify the correctness of your logic. Then TDD also forces us to have clear understanding of the outcome of particular function before implementing it, rather than touching things here and there blindly. Another important thing is that tests cases we write are acting as documentation on how to use that particular production code fragment. TDD also encourages us to write loosely coupled components, so they can easily be tested in isolation and, at higher levels.
Tools for TDD
To practice TDD you should also have some good Mock framework. If you are using java you can use either JMock or EasyMock, for .Net people there is a framework called NMock. Select Mock framework which matches your requirement and development platform.
Why we need Mocks
In OOP environment objects generally do not operate in isolation, rather they interact with each other to complete their operations.

These objects can be complex objects such as network access services, web services, data base services or they can be just POJOs.
When we write test case they should be able run independently and in isolations with others. If the test cases have to initiate web service or similar kind of complex objects, then that is not isolation. When testing our classes, we only want to test the functionality of that class only, we don't need to test the functionality of the web service it is depending on; for that(web service) we should have separate test case. For this reason we use Mock objects to mock the behavior of those complex classes.
This way we can mock the behavior of depending objects, and we can test our class independently and in isolation.
TDD Best Practices
Run tests frequently
Just having set of test cases won’t help much if you do not run them frequently. Another important thing is that when you do code changes in your production code you should start that from modifying test case fist. Otherwise if you just update your production code without warring to update test case; 1). You break TDD process and 2). You’ll end up with set of dead test cases.
Design to Fail
We need test cases to find faults in our code and report them, just writing test case to pass is not enough. Most important thing is that when the test fails, it should give enough details on why it failed, rather than just saying test failed. If it only says test fails then we'd have to debug and see why it failed; which can be quite time consuming thing. If a failing test clearly explains what has failed and why, we can quickly diagnose and correct the code. We can use techniques like having well names test cases, having informative assertion messages can help here.
e.g.
Customer customer = order.getCustomer();
assertEquals("10", customer.getAccountId());
assertEquals("2500", customer.getOustandingBalance());
ComparisonFailure: expected:<[2500]> but was:<[2512]>
Error report does not make it clear which of the assertions has failed. So we'll have debug and see what the real cause of test is failing. One solution would be to create two test methods, or we can add a message to identify the value being asserted.
assertEquals("outstanding balance", "2500", customer.getOustandingBalance());
ComparisonFailure: outstanding balance expected:<[2500]> but was:<[2512]>
Here we can immediately see what is the real cause of test failure.
Test behaviour, not Methods
I've explained this in my previous article.
Use Code Coverage Tool
By using a code coverage tool you can find out, up to what level your test cases had covered your production code. Sometimes when writing test case you may miss some scenarios, boundary points, etc... By using code coverage tool we can find out code fragments which not covered by any of the test cases. Sometimes this can also help us to find dead code. EMMA is a popular code coverage tool used for java language. You can find list of tools at http://www.codecoveragetools.com/
thanks
hi, I am a C++ developer and dealing with thousands of bugs already.
now thanks to you , now I know how to code better and test better.
what you telling is 100% correct. 99% time in debugging and testing and
1% time in coding.
--best regards--
thanks
hi, I am a C++ developer and dealing with thousands of bugs already.
now thanks to you , now I know how to code better and test better.
what you telling is 100% correct. 99% time in debugging and testing and
1% time in coding.
--best regards--
Thanks for an interesting article
Thanks for another interesting article Sandarenu.
TDD is a good concept which is not quite familiar to SL students until they get employed by a firm practicing it. It's good to see an introduction here.
There is also a slightly different approach (which is gaining traction lately) called Behavior Driven Development (BDD). I personally think BDD goes more streamlined with the developer workflows especially with practices like atomic coding iterations. Of course it has an Agile background. The Wikipedia article "Behavior Driven Development" is a good source get started. I apologize if I'm repeating what you already know, which is likely. :)
--
Gaveen Prabhasara
Post new comment