The tenets of Agile Methodologies have taken the programming world by storm leaving many to wonder if the merits of agile techniques are worth the investment. My exposure to the agile world has been our conversion from a standard software shop to one which embraces certain areas of agile methodologies. The biggest hurdle for me was to understand and apply the concepts of test-driven development to our daily production.
Test-driven development (TDD), as a concept, seems easy to understand at first glance, but is a little difficult to implement because of client imposed limitations. Software development in most shops is a stressful occupation. Schedules and features are often determined by the client’s needs and wants. Most clients are pushing to get the software as quickly as possible because of deadlines they have. This leaves little time for unexpected issues which creep into the development cycle. Many times developers are coding right to the last possible minute and testing takes place: if they have not run out of time; if they have the resources; or If they haven’t forgotten. Any testing which does take place at the development level is nothing more than quick bench testing to see that it works on the developer’s machine.
This software, when shipped to the client, is usually full of inconsistencies. As the client uses the software and suggests changes and bug fixes, more inconsistencies are introduced into the software as we strive to implement new features and fix existing problems. Over the course of several months or years, the code base becomes less clear. Changes and bug-fixes take longer to turn around and introduce other inconsistencies so that the code base reaches near complete entropy. At this point adding, extending, or fixing issues causes more problems.
Picture yourself standing waist deep in a pool. Around you are nearly 50 ping-pong balls floating in the water. Each ping-pong ball is a bug in your existing code base. Your job is to gather all fifty of the ping-pong balls in your arms and take them from the pool. In your attempts to gather them, as you with arms full of ping-pong balls, attempt to reach out and grab another one, one pops out from under your left arm. As you go to grab that one, two more pop out from your right side. No matter how you strive, you simply cannot get all of the balls from the pool in one session, unless you are extremely agile (pun intended).
Test-driven development was engineered to solve these kinds of problems, but there are generally a few problems when pitching the concept to management or to developers.
· The effort involved to change the developers routine
· The perceived doubling of time to accomplish testing and coding
· The expense involved
These are valid points which must be addressed; however, the benefits of TDD far outweigh the effort needed to put it into place in your organization. The effort necessary to change a developer’s routine is training. By showing the developer the benefits of writing tests first and building an archive of unit tests which will immediately point out if problems are introduced, you create more confidence and flexibility.
Many developer’s I’ve met say that to write the tests first and then write the code doubles the effort necessary to complete their assignments; however, in my experience, the opposite is in fact true. There is a synergistic coupling of writing tests and writing code which produces optimum code with nearly zero-defects in roughly the same amount of time. As you are thinking about what kinds of tests you need to write to test your new class, you are actually designing the code and writing it in your subconscious mind. When it comes to actually writing the code, the process is much quicker because of the unconscious effort extended in writing the tests.
There is an expense involved in the time it takes for training developers to become proficient in using the various test-driven packages, which include unit testing, asp.net testing, database testing, mocks, forms testing, etc. The mainstream testing products for .Net are: test classes (nUnit or MBUnit), mocks (nMock, TypeMock, and Rhino.Mock), and TestDriven.Net (a package which integrates unit testing into the VS IDE). Microsoft’s latest revision to Visual Studio’s IDE in Visual Studio 2008 has included directly integrated unit testing. If you are new to unit testing and TDD, you can begin the process of writing tests easily for a legacy project by simply right-clicking on the class in the edit window and choosing “Create Unit Tests”. Figure 1 shows a sneak preview of the code generated and we will delve into how to create these test classes in the next article in this series.
Figure 1. Tests created by VS2008
The costs of these three objections are outweighed by the benefits to the developer and to the company if you adhere to the tenets of test-driven development. The developer benefits because the red or green lights provide immediate feedback when running the unit tests as changes are made. Developers become more confident in making changes to complex code because of the existence of unit test coverage. There is also much less stress as development cycles shorten and bugs become more and more rare.
Companies which take advantage of TDD can:
· Establish realistic release cycles and release dates
· Release software with almost zero defects
· Achieve shorter development cycles
· Respond quickly and competently to client requests
TDD is not a panacea. It is a methodology which will take time and effort to introduce into your development arena, but the benefits far outweigh the few negatives proffered as excuses not to work competently and rapidly. For me, TDD started out as an alt.net fringe movement talked about in conferences by people with zero practical development experience. Now, because I have experienced TDD’s benefits, it has become a mainstay of my development process and has helped me to grow in confidence, flexibility and worth to my clients.