Geeks With Blogs
Blog Moved to http://podwysocki.codebetter.com/ Blog Moved to http://podwysocki.codebetter.com/
When creating my unit tests, I've been a big believer in the Object Mother pattern for creating state for my immutable value objects.  Basically, I need to put the objects in a valid state in the constructor.  Doing such is usually a pain, however.  Before the ObjectMother pattern, you had code similar to this to create an object in valid state, such as a medical claim.   Remember that we need hundreds of these to capture the variations in our model for our tests.

Claim claim = new Claim(
     new DateTime(2008, 1, 1),
     new Provider("Robert", "Jones",
          new Address("1800 28th St, NW", "Washington", "DC")),
     new Recipient("James", "Smith",
          new Address("1210 14th St, SE", "Washington", "DC")),
     new ClaimLineCollection(
          new ClaimLine("00308-1")));

Object Mother

As you can see, quite a mouthful for just one object in the correct state.  Instead, we could just mask it behind the Object Mother approach.  If you're unaware what the Object Mother pattern is, below is the basic idea.

Object Mother starts with the factory pattern, by delivering prefabricated test-ready objects via a simple method call. It moves beyond the realm of the factory by
  1. facilitating the customization of created objects,
  2. providing methods to update the objects during the tests, and
  3. if necessary, deleting the object from the database at the completion of the test.
So, let's come up with an example of this for our problem up above:

Claim claim = ClaimObjectMother.CreateFootSurgeryClaim();

And we would encapsulate the code from above to pass in the appropriate values to that.  But, soon, you'll find that your Object Mother is becoming a God-class and becoming cluttered with every variation that we can for unit testing the claims in our domain.  This can add up to a lot.

Test Data Builder

So, what are the alternate approaches?  What about a Test Data Builder?  And what is it anyways?  Well, it's just an extension of the Builder Pattern to create our test objects for testing our domain.  I got the inspiration after reading a post from Carel Lotz a while back.  Although he insists it's more of a DSL instead of the Builder Pattern.  And as you can note, this approach was combined with the Object Mother instead of using this as a complete alternate.

Let's take a look at an example of this:

public class ClaimBuilder
{
     private DateTime claimDate;
     private Provider provider = ProviderBuilder.StartRecording().Build();
     private Recipient recipient = RecipientBuilder.StartRecording().Build();
     private ClaimLineCollection claimLines = ClaimLinesBuilder.StartRecording.Build();

     public static ClaimBuilder StartRecording()
     {
          return new ClaimBuilder();
     }

     public ClaimBuilder WithClaimDate(DateTime claimDate)
     {
          this.claimDate = claimDate;
          return this;
     }
    
     public ClaimBuilder WithProvider(Provider provider)
     {
          this.provider = provider;
          return this;
     }

     public ClaimBuilder WithRecipient(Recipient recipient)
     {
          this.recipient = recipient;
          return this;
     }

     public ClaimBuilder WithClaimLines(ClaimLineCollection claimLines)
     {
          this.claimLines = claimLines;
          return this;
     }

     public Claim Build()
     {
          return new Claim(claimDate, provider, recipient, claimLines);
     }
}

As you can see, the implementation of a Builder pattern is rather easy.  But, how easy is it to implement our test cases?

Claim claim = ClaimBuilder.StartRecording()
     .WithClaimDate(new DateTime(2008, 1, 1))
     .WithProvider(ProviderBuilder.StartRecording()
          .WithName("Robert", "Jones")
          .WithAddress(AddressBuilder.StartRecording()
               .WithStreetAddress("1800 28th St, NW")
               .WithCity("Washington")
               .WithState("DC")
               .Build())
           .Build())
      .Build())
     .WithRecipient(RecipientBuilder.StartRecording()
          .WithName(James", "Smith")
          .WithAddress(AddressBuilder.StartRecording()
               .WithStreetAddress("1210 14th St, SE",)
               .WithCity("Washington")
               .WithState("DC")
               .Build())
           .Build())
      .Build())
     .WithClaimLines(ClaimLinesBuilder.StartRecording()
          .WithClaim("00308-1")
          .Build())
     .Build());

Conclusion

You can shorten things up a bit with these builders to not be as verbose as I am right here.  I could not care about certain parts of my domain when building these objects and choose to fill in only things I need to in order to my tests to pass.  Overall, I think this helps the readability of the test data that I am using.  What's really powerful is having builders interact with other builders to create complete test cases for our domain.  I think I'm leaning towards this for my Entity objects as well.  I'll continue looking at this and trying to tweak it a bit.

kick it on DotNetKicks.com Posted on Tuesday, January 8, 2008 1:11 AM .NET , Test Driven Development , Domain Driven Design | Back to top


Comments on this post: Object Mother Pattern versus Test Data Builder Pattern

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
Take a look at my open source project NBuilder. http://www.nbuilder.org

It is a generic implementation of the test data builder pattern and allows you to rapidly create objects, lists of objects and object hierarchies. It's also very configurable and extendible.
Left by Gareth on Apr 20, 2009 4:11 PM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
The point of the Test Data Builder pattern is to allow a test to *only* specify the aspects of the data that are significant to the test, and let the builder provide safe defaults for the rest. So, a test using Test Data Builders should be both as terse and as readable (if not more so) than a test using an Object Mother.
Left by Nat on Jun 23, 2009 7:52 AM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
I have been using ObjectMother pattern in my project. i had a small doubt. In the mother object should we create concrete object or we could use a stub using any of the dynamic mocking framework like Rhino Mocks?
Left by Nilesh Gule on Oct 12, 2009 11:35 PM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
I am looking forward for your next post on this topic.Your posts really do the help.Thank you! http://www.clothingseries.com mens gucci t shirts to us!
Left by beauty on Jun 11, 2010 2:31 AM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
Hot design and newest collection at unbelievable prices. Charmed by the magic of amazing tattoo and impressive color. Always your first and best choice!!!
Left by smile on Jun 23, 2010 7:07 PM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
Firstly can we reasonably assume that any policy NOT in either the Tory or LibDem manifestos by defintion does not have any mandate because it was never laid before the electorate
Left by Nike Air Force on Jun 14, 2011 9:23 PM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
It looks made for Hushovd who likes those kinds of things.
Left by cheap uggs on Oct 16, 2011 9:00 PM

# re: Object Mother Pattern versus Test Data Builder Pattern
Requesting Gravatar...
It seems like hell breaks loose for a sole object to be in the correct state. That code is long, I give my whole respect to the one who has the patience to do this all over again. A good job requires a lot of work, indeed.
Left by Trend Micro cloud security on Jun 19, 2012 8:41 AM

Your comment:
 (will show your gravatar)


Copyright © Matthew Podwysocki | Powered by: GeeksWithBlogs.net