22 IEEE SOFTWARE May/June 2002 0740-7459/02/$17.00 © 2002 IEEE O ne thing that makes unit-testing code so hard is the way the real world keeps intruding. If all we had to do was code up tests for methods that sort arrays or generate Fibonacci se- ries, life would be easy. But in the real world we have to test code that uses data- bases, communications devices, user inter- faces, and external applications. We might have to interface to devices that aren’t yet available or simulate network errors that are impossible to generate locally. This all con- spires to stop our unit tests from being neat, self-contained (and orthogonal) chunks of code. Instead, if we’re not careful, we find ourselves writing tests that end up initializ- ing nearly every system component just to give the tests enough context to run. Not only is this time consuming, it also intro- duces a ridiculous amount of coupling into the testing process: someone changes an in- terface or a database table, and suddenly the setup code for your poor little unit test dies mysteriously. Even the best-intentioned de- velopers become discouraged after this hap- pens a few times. Eventually, testing starts to drop off, and we all know where that leads. Fortunately there’s a testing pattern that can help. Using mock objects, you can test code in splendid isolation, simulating all those messy real-world things that would otherwise make automated testing impossi- ble. And, as with many other testing prac- tices, the discipline of using mock objects can improve your code’s structure. An example: Testing a servlet Servlets are chunks of code that a Web server manages. Requests to certain URLs are forwarded to a servlet container (or man- ager) such as Jakarta Tomcat (http://jakarta. apache.org/tomcat), which in turn invokes the servlet code. The servlet then builds a re- sponse that it sends back to the requesting browser. From the end user’s perspective, it’s just like accessing any other page. Figure 1 shows part of the source of a trivial servlet that converts temperatures from Fahrenheit to Celsius. Let’s quickly step through its operation. When the servlet container receives the request, it automati- cally invokes the servlet method doGet(), passing in two parameters, a request and a response. (These are important for our test- ing later). The request parameter contains information about the request; the servlet’s job is to fill in the response. The servlet’s body gets the contents of the field “Fahren- heit” from the request, converts it to Cel- sius, and writes the results back to the user. The writing is done via a PrintWriter object, which a factory method in the response ob- ject provides. If an error occurs converting the number (perhaps the user typed “boo!” software construction Mock Objects Dave Thomas and Andy Hunt Editors: Andy Hunt and Dave Thomas The Pragmatic Programmers andy@pragmaticprogrammer.com dave@pragmaticprogrammer.com Yet sit and see; Minding true things by what their mockeries be. —Shakespeare, Henry V