Mock object is basically a mirage of the real object as they posses the same qualities by don't do anything. Mock objects really shines when working with some entity that continuously changes like time, temperature, air speed etc. In this post I will introduce mock objects and how can they be useful when unit testing such entities.

I took the idea from a great article published on AspAlliance. The article "Beginning to Mock Using Rhino Mocks and MbUnit" is written by Ben Hall. The idea is that we are testing that your method returns the correct image. The correctness of the image depends on the time of the day. So, if it is day time then "sun.jpg" is returned and if it is night time then "moon.jpg" is returned. Let's first see the implementation without using the Mock objects.

The above method is used to test for the image during the day time. Let's check out the implementation of the ImageOfTheDayService.GetImage method.

public static string GetImage(DateTime dt) { int hour = dt.Hour;

if (hour > 6 && hour < 21) return "sun.jpg";

return "moon.jpg"; }

The problem is that you can only test the day time result during the day and the night time result during night. This is inconvenient. You can hack the implementation of your tests and force the day time and night time to happen. Check out the implementation below:

In the should_return_sun_image_when_it_is_day_time test I am using 5:00 AM as the start time. The problem is that 5:00 AM is still night (according to the demo application). In order to a successful test I need to provide the day time. So, I do some funky stuff and crank the time to 3:00 PM which is the time during the day. Now, I test my GetImage method using the new fake time.

The funky hack makes the test pass but leaves behind ugliness in the test methods. Now, let's introduce the Mock objects to clear out this mess. I am using Moq framework to create my mock objects but you can use any framework you like. First, I need to create an interface for the DateTime which I can feed to the Moq framework to return me a mocked object.

public interface IDateTime { int GetHour(); }

Now, the GetImage method of the ImageOfTheDayService will take the IDateTime as the parameter instead of the DateTime.

The test becomes much simpler now. All we are saying is that we expect a call on the "GetHour()" method of the IDateTime interface. The method will return "15" (day test). We are not concerned about what is the current time of the day since we are putting expectations and results. Finally, we pass the IDateTime to the GetImage method and compares the output with our expected results.

The call to DateTime.Now might ultimately need to be a member of ITimeService at some point if it ends up needing to be mocked, but at this point, this implementation is the simplest thing that could possibly work based on my current understanding of the requirements and the needs of the implementation.

There are a few alternative designs that would suit here, all of which would not have required creating an adapter for DataTime, and would ultimately lead to rich, intent-revealing and natural API for your domain.

Ultimately, I would be suspect of the method signature:

public static string GetImage(ITimeService time)

It has two design smells:- It's static- It accepts a service interface as its argument (method injection)

The method might be perfectly fine, but it's on yellow alert for the time being.

[Test] public void MOCKING_should_return_night_image_when_it_is_night_time() { // System will think that it is night time using (Recorder r = new Recorder()) { r.ExpectAndReturn( DateTime.Now.IsDayTime(), false); }

What I usually watch for in my tests is excessive setup. Here, you have to do a lot of time-related setup in order to return one of two images. It's perfect for an integration test, but for a unit test you just need a boolean value. Having realized that, I would write a test for ImageProvider.GetImage(bool IsDayTime) and another for DayService.IsDayTime(this DateTime time).

My point is, sometimes we need neither DI nor mocks. We can have two classes totally decoupled, and unit tests as simple as they can be. If we make testability our guide to a better design, we often end with several small independent classes that can be tested without mocks.

Still, mocking is a very powerful technique, and there are times when you can't do without it.