CodeBetter.Com
CodeBetter.Com
RSS 2.0 via Feedburner
           Do you Twitter? Follow us @CodeBetter

Jeremy D. Miller -- The Shade Tree Developer

Under the hood and working with .Net, TDD, Software Design, and Agile Stuff

December 2005 - Posts

  • Why and When to Use Mock Objects

    In the last post I introduced mock objects and talked about some of the various flavors of fake objects.  In this post I want to talk about when and why you would use a mock object.  The main benefit of using mock objects is increased testability throughout a system.  A secondary benefit of mock objects is an improved ability to do continuous design within your code.

     

    Improved Unit Testing

     

    Let’s look at the usage of mock objects applied to the desired qualities of a good unit test.

     

    • Unit tests should be atomic.  TDD style unit tests should be small tests that cover a specific, granular area of the code.  The code under test might interact with other classes or external systems, but at the moment you only want to worry about the proper functioning of the class under test.  You can preserve the atomicity of the unit test by replacing the external resources and coding dependencies by using a mock object to establish an expected behavior.  You specify exactly how the mock object is going to behave, so any unit test failures are now traced to the class under test.  When I was an engineer one of the hardest tasks in any engineering calculation was modeling boundary conditions.  A boundary condition is a point in the system with known behavior.  Inside your calculation you could ignore anything outside the boundary conditions.  The way to make your life easier was to establish boundary conditions so as to minimize the number of variables within any engineering calculation.  Mock objects are conceptually the same thing as boundary conditions.  One of the primary claims for the efficiency of TDD is the radically reduced time spent debugging code.  My experience that claim is true, but only when you write fine-grained tests.  My ratio of debugging time to coding time dropped precipitously when I started to become proficient with mock objects.  Please be aware that excessive mocking calls in a unit test can lead to unit tests that are too tightly coupled to the internal implementation of the very dependency you’re trying to mock.  This can make your code very difficult to refactor because the unit tests are brittle.
    • Order Independent and Isolated.  You should never assume that the tests are run in any certain order.  Each test should start from a completely known state and clean up after itself if necessary.  One of the biggest mistakes in writing unit tests is allowing state or the results of one unit test effect a different unit test.  It’s hard enough to troubleshoot testing failures.  Having to look through other unit tests to find the problem is time intensive and counterintuitive.  Static properties, singletons, and repositories are a common culprit, but the worst culprit might be testing against the database.  The entire purpose of a database is to maintain state, and that’s not a particularly good trait inside a unit test.  Using a mock object in place of any kind of stateful dependency will isolate your unit test from external state and make your unit tests order independent and isolated.
    • Intention Revealing.  This quality goes back to interaction based testing.  If the responsibility of the class being tested is to direct or coordinate other classes, then using a mock object inside the test may make the test easier to understand.  On the other hand, excessive mock object setup may make the unit test a lot more difficult to understand.  My advice is to simply pay attention to what you’re coding.  If it feels like using a mock object is making the test harder, back up and find a different way to write the test or change the class structure.    I’m going to come back to this topic quite a bit more in a later post.  I got pretty irritated at a junior/junior pair last year when I found out they had spent the better part of a day trying to write a unit test by mocking ADO.Net with no real success.  When I saw what they were doing I convinced them to change direction and create a new coarse-grained interface that would encapsulate the ADO.Net calls and would be easy to mock.
    • Easy to Setup.  This quality might be a bit in the eye of the beholder.  I’ll talk about this in much more detail in the next post or two, but a lot of mock scaffolding in a unit test is a code smell.  One very significant reason to use mock objects is to avoid the need to setup external resources into a known state for each test.  Think of a database.  You might only need a particular row in the database for the test, but due to the (necessary) evil of referential integrity that one row might require a whole bunch of other data first.  Even worse is something like a web service, a messaging queue, or the all time worst IMO – Active Directory.  More specifically, here’s a list of reasons to forgo trying to setup an external resource to behave in an expected way:
      • It’s often more work to write the SQL scripts than it is to setup the mock expectations or stub returns.  Less work is always good
      • Setting up the external state often obfuscates the test and can make the test harder to understand
      • Having external resource setup inside an automated test often tightly couples that test to the inner workings of the external dependency.  Loose coupling in automated tests is every bit as important for success as loosely coupled code.
    • Runs Fast.  Making your automated tests run quickly isn’t a luxury, it’s a necessity.  Except for the very beginning of a project you should expect automated testing to be the performance bottleneck in your automated build process.  It’s not a good thing when you start frequently hearing the phrase “we’re in CC.Net time.”   I had a post on this a while back here.

     

     

     

    Designing for and with Mock Objects

     

    I love the “mock as spy” analogy, but here’s an additional way to think about the role of a mock object.  In the movie and TV industries child actors are expressly limited in the number of hours they’re allowed to work in a day or week.  The director will use adults of roughly the same size to be “stand-ins” for the child actors so they can accurately storyboard the scene with the set, the lights, and the camera angles (I know all about this because of a classic Seinfeld episode years ago).  The director and the camera crew can get the scene completely setup without cutting into the child actors’ limited quota of hours.  Mock objects can be used in much the same way.  It’s what I like to think of as “Client First Development.”  Falling back on the Model View Presenter pattern as an example yet one more time, you might build a screen in a couple pieces:

     

    1. Presenter – handles the user information flow logic and intermediates communication between the actual screen and the backend services
    2. IService/Service – the gateway to the backend business or service layer
    3. IView/View – The actual screen

     

    In this case I would define Presenter as the client of the services provided by the IService and IView interfaces.  I’ve consistently found it to be more efficient to make the development of the Presenter (the client) drive the signature of the IService and IView interfaces.  The Presenter is largely coded first with the dependencies mocked.  I’ve found this approach to be consistently more efficient than trying to drive the development from backend to front.  The requirements of “service provider” classes or modules are completely determined by the needs of their clients.  Building a service provider before the client will very frequently result in rework to the service provider when you discover that the client has different needs than you previously expected.  By using mocks or stubs I can narrowly focus on the design of the client and then turn and implement the resulting interfaces for the service provider.  Yeah you can give me the tired old line of “if you just did more research upfront…” but no design can ever accurately said to be “done” until it’s fully implemented and tested.

     

    Another way to think about mock objects is that they’re like doing a UML sequence diagram, but in code. 

     

    I’ve sarcastically described TDD in the past as Mock-Driven Design, but it does work.  You need to very consciously consider testability in almost every design decision.  Very purposely consider how to spread responsibilities between classes to maximize testability.  I am very much cognizant of utilizing mock objects when I do class and namespace level design.

     

     

    Here’s a quote from Jeffrey Palermo this very afternoon – “do you know how nice it is to get a piece of code into NUnit or the debugger without having to install every single other service?”  Yes Jeffrey, I know exactly how you feel.

     

    What to Mock?

     

    So we come to the question of what to mock?  My rule of thumb is to mock anything that is involves any kind of call or access to things outside of the AppDomain.  Mocking the data access layer when you’re testing business or service layer logic is an obvious example.  Here are some other examples that I can remember using:

     

    • WinForms code
    • ASP.Net objects – user controls, HttpContext objects (but I’d advise against doing this directly)
    • Web service proxy classes.  Absolute no-brainer. 
    • Database access code, persistence
    • Active Directory access
    • Gateways to weird legacy code or systems – and almost all legacy code IS weird
    • Facades to other subsystems
    • Remoted classes

     

     

    Next up is a discussion on the best practices for mock objects, including a section on when NOT to use mock objects.

  • Mock Objects and Stubs: The Bottle Brush of TDD

    I’m in a dry spell for blogging, so here’s a rehash of a presentation I gave internally at work earlier this year.  The general topic of mock objects comes up pretty often at our Agile Austin lunches, so I figure mocks are worth some blogging space anyway.  This is the first of 4 posts on the subject of mock objects and stubs.

     

    1. Introduction to Mocks and Stubs (this post)
    2. When and Why to use Mocks and Stubs
    3. Best Practices for Mocks
    4. Constraints and other Mocking Tricks
    5. Attaching Mocks and Stubs with StructureMap (by request)

     

     

    Test Driven Development always seems pretty simple in the introductory tutorials.  Assert that the result of 2 + 2 equals 4, check.  Then Monday morning you go back to the real world of enterprise application development and you’re suddenly faced with relational databases, middleware, web services, and all manner of security infrastructure.  For a variety of reasons, interacting with external resources can make your automated tests a lot harder to write, debug, and understand.  Even worse, those external resources may make your tests indeterminate (think shared database).  You’ll frequently hear teams say they didn’t write unit tests for a particular area of the code because it was just too hard to test.  I think one of the biggest challenges of using TDD is learning strategies for isolating the code that’s hard to test and writing code that is easy to test.  One of the primary strategies to extend unit test coverage into those hard to reach places is to use mock objects, stubs, or other fake objects in place of the external resources so that your tests don’t involve the external resources at all.

     

    One of the central pillars of Object Oriented programming is polymorphism -- the ability to interchangeably utilize multiple implementations of a well-defined interface.  We’ve all seen way too many silly examples of Beagle inheriting from Dog which implements IAnimal.  Here’s a more realistic and powerful utilization of polymorphism.  You’re tasked with building a new reporting website to display data from the old legacy COBOL inventory system (you know, the one where the column names are COL0023 and the tables are D05A10).  The legacy system team is struggling to get the data access code done because the database structure doesn’t make the slightest bit of sense.  You’d like to get started with constructing the website, so you define the interface of the data access class and create a stub class that just reads data from an xml file instead of the legacy code.  You can get on with your work and focus on the user interface functionality.

     

          public interface IDataSetSource

          {

                DataSet FetchReport(DateTime from, DateTime to);

          }

     

          public class StubbedDataSetSource : IDataSetSource

          {

                public DataSet FetchReport(DateTime from, DateTime to)

                {

                      DataSet dataSet = new DataSet();

                      dataSet.ReadXml("ReportData.xml");

     

                      return dataSet;

                }

          }

     

          public class DataSetSource : IDataSetSource

          {

                public DataSet FetchReport(DateTime from, DateTime to)

                {

                      // run a query or a stored procedure against the database and return

                      // a DataSet of the results

                }

          }

     

          // ReportController depends on the IDataSetSource interface, not a particular

          // implementation or even backend data store

          public class ReportController

          {

                private IDataSetSource _source;

     

                public ReportController(IDataSetSource source)

                {

                      _source = source;

                }

          }

     

    What’s the Difference between a Mock and a Stub?

     

    Stubs have been around as long as object oriented programming and they’re well understood.  Mock objects on the other hand are a relatively new concept that seems to generate a great deal of confusion.  A common misconception about mocks and stubs is that the difference is that stubs are static classes and mocks are dynamically generated classes created by some kind of tool like NMock.  That’s a false dichotomy.  The real difference between a mock and a stub is in the style of unit testing, i.e. state-based testing versus interaction testing.  A stub is a class that is hard-coded to return data from its methods and properties.  You use stubs inside unit tests when you’re testing that a class or method derives the expected output for a known input. 

     

    A mock object is a tool for interaction based testing.  You use a mock object to record and verify the interaction between two classes.  Roy Osherove made my all time favorite explanation of mock objects by comparing a mock object to a spy that listens to the interaction between two classes. 

     

    The typical usage of a mock object is roughly the 5 step process below.

     

    1. Create the mock object
    2. Set the expectations on the mock object
    3. Create the class that’s being tested
    4. Execute the method that’s being tested
    5. Tell each mock object involved in the test to verify that the expected calls were made

     

    Here’s an example from a model view presenter pattern using NMock to create dynamic mock objects.

     

                [Test]

                public void CloseViewWhenViewIsNotDirty()

                {

                      // 1.) Create the mock objects

                      IMock msgBoxMock = new DynamicMock(typeof(IMessageBoxCreator));

                      IMock viewMock = new DynamicMock(typeof(IView));

     

                      // 2.) Define the expected interaction

                      msgBoxMock.ExpectNoCall("AskYesNoQuestion", typeof(string), typeof(string));

                      viewMock.ExpectAndReturn("IsDirty", false);

                      viewMock.Expect("Close");

     

                      // 3.) Create the presenter class with the mock objects

                      Presenter presenter = new Presenter(

                            (IView) viewMock.MockInstance,

                            (IMessageBoxCreator) msgBoxMock.MockInstance);

     

                      // 4.) Perform the unit of work

                      presenter.Close();

     

                      // 5.) Verify the interaction

                      msgBoxMock.Verify();

                      viewMock.Verify();

                }

     

    Dynamic versus Static

     

    Both mocks and stubs can be implemented as either a dynamically emitted class or a static class that you roll on your own.  Here’s an example stubbing security done both statically and dynamically.

     

          public interface ISecurityDataStore

          {

                bool Authenticate(string userName, string password);

                string[] GetRoles(string userName);

          }

     

          // Static stub

          public class StubbedSecurityDataStore : ISecurityDataStore

          {

                public bool Authenticate(string userName, string password)

                {

                      return true;

                }

     

                public string[] GetRoles(string userName)

                {

                      return new string[]{"Admin", "Write", "Read"};

                }

          }

     

          [TestFixture]

          public class AuthenticationTester

          {

                public void AuthenticateSuccessfullyAndCreateTheCorrectPrincipal()

                {

                      // Create a dynamic mock object for ISecurityDataStore, but use it

                      // like a stub.  I don't call Verify() on the dataStoreStub object

                      // because I'm just testing the state of the GenericPrincipal object

                      // that is returned by authenticator

                      IMock dataStoreStub = new DynamicMock(typeof(ISecurityDataStore));

                      string[] theRoles = new string[]{"role1", "role2"};

     

                      // setup dataStoreStub.MockInstance to return theRoles anytime the "GetRoles" method

                      // is called

                      dataStoreStub.SetupResult("GetRoles", theRoles, null);

     

                      Authenticator authenticator = new Authenticator((ISecurityDataStore)dataStoreStub.MockInstance);

     

                      GenericPrincipal principal = authenticator.CreatePrincipal("Jeremy", "ComplexPassword");

                     

                      Assert.IsTrue(principal.IsInRole("role1"));

                      Assert.IsTrue(principal.IsInRole("role2"));

                      Assert.IsFalse(principal.IsInRole("role3"));

                }

          }

     

    We’ve already looked at several examples of dynamic mocks, so here’s an example of what a static mock for ISecurityDataStore might look like.

     

          public class MockSecurityDataStore : ISecurityDataStore

          {

                private string _expectedUserName;

                private string _expectedPassword;

                private string[] _roles = new string[0];

                private bool _authenticationSuccess = false;

                private bool _authenticateWasCalled = false;

     

                public MockSecurityDataStore(string expectedUserName, string expectedPassword, bool authenticationSuccess)

                {

                      _expectedUserName = expectedUserName;

                      _expectedPassword = expectedPassword;

                      _authenticationSuccess = authenticationSuccess;

                }

     

                public string[] Roles

                {

                      get { return _roles; }

                      set { _roles = value; }

                }

     

                public bool Authenticate(string userName, string password)

                {

                      Assert.AreEqual(_expectedUserName, userName, "Unexpected user name");

                      Assert.AreEqual(_expectedPassword, password, "Incorrect password");

     

                      _authenticateWasCalled = true;

     

                      return _authenticationSuccess;

                }

     

                public string[] GetRoles(string userName)

                {

                      Assert.AreEqual(_expectedUserName, userName, "Unexpected user name");

                      return _roles;

                }

     

                // Call this method to verify the Authenticate() method was called at all

                public void VerifyExpectations()

                {

                      Assert.IsTrue(_authenticateWasCalled, "The Authenticate() method was never called");

                }

          }

     

    I definitely have my preferences in the static versus dynamic mock debate, but at various times I’ve used all four permutations.  I like to use static mocks whenever I’m faced with a lot of name/value pairs or set based arguments.  I have a static mock class in my rough equivalent of the Enterprise Library’s data access framework that validates the correct parameter values for the invocation of any database command (I still think it’s a clever implementation, but we don’t use it very often).  Whatever your preference, I’d still try to be familiar with all of the options because each development project is different.  By all means, don’t blow off the dynamic mock tools just because they look scary at first view.

                                                                                                

    The Case for Dynamic Mocks

     

    My strong preference is to use dynamic mocks.  A lot of people avoid using dynamic mocks because they look weird at first and maybe aren’t the easiest thing in the world to understand.  I think that once you get past the initial learning curve dynamic mocking engines like NMock or RhinoMocks become easier to use.  I like dynamic mocks because you don’t have to clutter up your code with a bunch of extra classes for the static mocks.  Another great attribute of dynamic mocks is that you don’t have to implement the entire interface and you can essentially ignore the methods and members of the interface being mocked that aren’t involved in any particular unit test.  I really get irritated when I add a new method to an interface then spend a couple minutes chasing down all of the static mocks and stubs to add skeleton methods just to get the code to compile.  I also think that dynamic mocks are more flexible.  I’ve also found that dynamic mocks lead to writing less code because the mocking engine takes care of the assertion logic.

     

    The Case for Static Mocks

     

    The single biggest reason to use static mocks is simply a discomfort with dynamic mock engines.  I’ll easily grant you that the dynamic mock tools aren’t very well documented and they’re still relatively new.  Micah Martin of ObjectMentor has a good post on the pro-static mock case.  I don’t agree with Micah entirely, especially about his contention that mock tools aren’t flexible enough (but that’s a later post already on the way).  Where he’s definitely accurate is in warning us that dynamic mocks hamper refactoring.  Dynamic mocks aren’t “ReSharper-able.”  The compiler and ReSharper can’t find the method references in mock.ExpectAndReturn(“SomeMethod”, true) when you change the SomeMethod() to IsSomething().  The refactoring challenge in specific is why I’m taking a long, hard look at RhinoMocks to replace NMock in our development (that little Intellisense thing is pretty important too).

     

    There’s a more general lesson in there though.  Using reflection of any kind can easily lead to brittle code that is harder to refactor.

     

     

     

     

    Next up is a discussion on when and why to use mock objects…

  • Preaching to the choir

    We got into a bad cycle in our standup meeting about one of those sticky production situations with no good, easy solution.  It's a real problem and I don't mean to make light of it, but it spawned a great quote.  One of my coworkers was trying hard to convince us to go a certain path, with everyone else saying bah humbug things like "we can't do that until after the first of the year" or "we don't understand the impact yet" or "he doesn't have time to research that right now." 

    My boss ultimately tried to defuse the situation with:

    "You're preaching to the choir.  It's so bad that I'm like the church secretary that you're having an affair with"

     

    My favorite quote, though, from a consulting gig was "let's stop beating the choir."

  • Occam's Razor for Debugging

    Occam's Razor

    Let's all remember to check out the simplest, easiest to check causes first anytime we're debugging a testing or production defect.  If nothing else, knock the simple explanations off the list of possibles quickly before you consider anything more complex.  We had a case today where a data validation message in the test environment was wrong, but the FitNesse test in our build environment was correct.  Simplest explanation?  The deployment to testing wasn't correct.  Actual explanation?  The deployment to testing was incorrect.  That should have been the very first thing to check, but it wasn't.

    We had a manual post-step in a build process that was missed.  That'll be automated by the end of day tomorrow to stop that problem in its tracks.  Grrr.

More Posts

Our Sponsors

Free Tech Publications

This Blog

Syndication

News

All opinions expressed here constitute my (Jeremy D. Miller's) personal opinion, and do not necessarily represent the opinion of any other organization or person, including (but not limited to) my fellow employees, my employer, its clients or their agents.

About Me

"Best Of" Compendium

StructureMap (Dependency Injection for .Net)

StoryTeller (Supercharged Fit)

Build your own Cab

TestDriven

MVP