Dummy, Fake, Stub, and Mock

Mock is a generic term that covers a family of stand-in objects for use in unit testing.

Dummy:
Dummy objects are simple mocks. Generally dummy objects are stands for an external resource. When a method is invoked they usually return a predefined response for a method. They usually can’t vary the response based on input parameters.

Following examples shows how to use Dummy object to test using a dummy object:
Here we have a class called Dependent class with following definition:

internal class DependentClass
{
	private readonly IDependency _dependency;
	public DependentClass(IDependency dependency)
		{
			_dependency = dependency;
		}
		public int GetValue(string s)
		{
			return _dependency.GetValue(s);
		}
}

Inside above class we passed IDependency interface by constructor. The definition of IDependency is as follows:

internal interface IDependency
{
	int GetValue();
}

Though we passed IDependency interface through the constructor of Dependent class so Dependent class has the dependency of a class that implements IDependency interface. Dependent class has a method called GetValue(). This method takes a string as argument and returns the GetVlue() method of the implementation of IDependency interface.
Now we’ll check how we’ll test the Dependent class using dummy object. First of all we’ll create a class named DummyDependency that will implement IDependency interface as follows:

public class DummyDependency : IDependency
{
	public int GetValue(string s)
	{
		return 1;
	}
} 

Then we’ll test as follows:

[TestFixture]
public class DummyTestClass
{
	[Test]
	public void TestWithADummy()
	{
		var dependency = new DummyDependency();
		var dependentClass = new DependentClass(dependency);
		const string param = “abc”;
		const int expectedResultOne = 1;
		var resultOne = dependentClass.GetValue(param);
		Assert.AreEqual(expectedResultOne, resultOne);
	}
} 

Inside above code we created an instance of DummyDependency class. Then passed that instance as the constructor value of Dependent class. The test calls GetValue() method of Dependent class. We passed “abc” as the parameter value of GetValue() method. The DummyDependency class has an implementation of GetValue that simply returns the value 1.
This satisfies the test; the value 1 is the expected result and the dummy object DummyDependency satisfies that requirement.

But above implementation of dummy object has limitations. When the value is passed in the test the dummy object can react only one way i.e. returns the value 1. In some cases this limitation is not any issue but for most tests where we have to verify the domain business logic more robust mocking is necessary.

Fakes and Stubs
Fakes and stubs are a step up from dummy objects. They can vary their response based on input parameters. For example, a stub of a database may return the name Rick Nash for user ID 61 and the name Steve Mason for user ID 1. Aside from that, no logic is invoked. A stub generally cannot track how many times a method was called or in what order a sequence of methods were called. An example of a stub is provided here:

	[TestFixture]
	public class StubTestClass
	{
		[Test]
		public void TestWithAStub()
		{
			var dependency = new StubDependency();
			var dependentClass = new DependentClass(dependency);
			const string param1 = “abc”;
			const string param2 = “xyz”;
			const int expectedResultOne = 1;
			const int expectedResultTwo = 2;
			var resultOne = dependentClass.GetValue(param1);
			var resultTwo = dependentClass.GetValue(param2);
			Assert.AreEqual(expectedResultOne, resultOne);
			Assert.AreEqual(expectedResultTwo, resultTwo);
		}
	} 

	public class StubDependency : IDependency
	{
		public int GetValue(string s)
		{
			if (s == “abc”)
    			return 1;
			if (s == “xyz”)
   			 return 2;

			return 0;
		}
	} 

Above example creates a new class called StubDependency that implements the IDependency interface. Unlike the DummyDependency , the implementation of GetValue on StubDependency has some logic to returned different values based on different input parameters.
This stub is able to respond to different condition in different specific ways. This provides a much more robust way of mocking than dummy objects.

Mock
A mock is a step up from fakes and stubs. Mocks provide the same functionality as stubs but are more complex. Mocks have defined rules. These rules say in what order methods must be called on their API. Most mocks can track how many times a method was called and can react based on that information. Mocks generally know the context of each call and can react differently in different situations. Because of this, mocks require some knowledge of the class they are mocking.

Following is the example of a mock. Here we’ve have a few members to the IDependency interface and Dependent class as follows:

internal interface IDependency
{
	int GetValue(string s);
	void CallMeFirst();
	int CallMeTwice(string s);
	void CallMeLast();
}
internal class DependentClass
{
	private readonly IDependency _dependency;
	public DependentClass(IDependency dependency)
	{
		_dependency = dependency;
	}
	public int GetValue(string s)
	{
		return _dependency.GetValue(s);
	}
	public void CallMeFirst()
	{
		_dependency.CallMeFirst();
	}
	public void CallMeLast()
	{
		_dependency.CallMeLast();
	}
	public int CallMeTwice(string s)
	{
		return _dependency.CallMeTwice(s);
	}
}

IDependency interface and the DependentClass class includes following three methods:
+. CallMeFirst ,
+. CallMeTwice and
+. CallMeLast .
In many APIs specific methods have to be called in a specific order. Also methods need to be called a specific number of times. In our case method names of IDependency and DependentClass indicates when and how many times it would be called i.e.
+. CallMeFirst must be called first and for one time,
+. CallMeTwice method must be called second and for two times and
+. CallMeLast method must be the last method called for a particular transaction.

To enforce these rules, we need to write a more sophisticated and complex mocking class as follows:

public class MockDependency : IDependency
{
	private int _callMeTwiceCalled;
	private bool _callMeLastCalled;
	private bool _callMeFirstCalled;
	public int GetValue(string s)
	{
		if (s == “abc”)
			return 1;
		if (s == “xyz”)
			return 2;

		return 0;
	}
	public void CallMeFirst()
	{
		if ((_callMeTwiceCalled > 0)|| _callMeLastCalled)
			throw new AssertionException(“CallMeFirst not first method called”);
	_callMeFirstCalled = true;
	}

	public int CallMeTwice(string s)
	{
		if (!_callMeFirstCalled)
			throw new AssertionException(“CallMeTwice called before CallMeFirst”);
		if (_callMeLastCalled)
			throw new AssertionException(“CallMeTwice called after CallMeLast”);
		if (_callMeTwiceCalled > = 2)
			throw new AssertionException(“CallMeTwice called more than twice”);

		_callMeTwiceCalled++;

		return GetValue(s);
	}
	public void CallMeLast()
	{
		if (!_callMeFirstCalled)
			throw new AssertionException(“CallMeLast called before CallMeFirst”);
		if (_callMeTwiceCalled !=2 )
			throw new AssertionException(string.Format(“CallMeTwice not called {0} times”,_callMeTwiceCalled));

		_callMeLastCalled = true;
	}
}

To be sure that the methods of the implementation of IDependency used by the DummyClass are used correctly it’s necessary to build a mock that not only returns values, but encapsulates all the rules of the API. Each method must check to make sure that it’s been called in the correct order. In the case of CallMeTwice the method must also verify that it has been called the appropriate number of times.

Some important points about mocking
+. Hand rolling mocking is inefficient, time consuming and introduces a huge amount of fragility in our code. For that reason most developers choose to employ a mocking framework and avoid hand-rolling mocks.
+.Hand rolling mock dependency class required to have quite bit of knowledge of how dependent class uses it. So developers need to have a clear understanding about object oriented programming and good coding practice.

Following tests the DependentClass implementation that uses an implementation of IDependency based on MockDependency is listed here:

	[TestFixture]
	public class MockTestClass
	{
		[Test]
		public void TestWithAMock()
		{
			var dependency = new MockDependency();
			var dependentClass = new DependentClass(dependency);
			const string param1 = “abc”;
			const string param2 = “xyz”;
			const int expectedResultOne = 1;
			const int expectedResultTwo = 2;
			dependentClass.CallMeFirst();
			var resultOne = dependentClass.CallMeTwice(param1);
			var resultTwo = dependentClass.CallMeTwice(param2);
			dependentClass.CallMeLast();
			Assert.AreEqual(expectedResultOne, resultOne);
			Assert.AreEqual(expectedResultTwo, resultTwo);
	}
}

When to use which?
There are so many options for mocking e.g. dummy, fake, stub and mock. So there is a common question is when to use which. The answer is that it depends on the situation. Dummy can be used where no business logic exists. It usually returns predefined response. Fake and stub are useful when no logic exists and need to vary the response based on input parameters. Mocks are useful when you need to replicate a more complex interaction with a component, but they usually require more configuration and overhead than is needed for most unit tests. Favoring stubs also ensures that you are designing your system to be loosely coupled; requiring a calling method to know an extensive set of rules to use an API is not very loose. Finally, you should use a spy when a method on a mocked resource does not have a conventional output.

Md. Mojammel Haque
Currently working as Lead Team (Application Architecture) at Raven Systems Ltd.

Passion for software development especially agile practices such as TDD & BDD with in depth knowledge of OOP, DDD, CQRS, ES, GoF, SOLID and PoEAA.

Over 6 years of software development experience ASP.NET. Has the ability to understand and transform complex business requirements into software ensuring applications are delivered on time.

Also experience in non Microsoft .NET technologies such as Dapper.Net, Subversion, Structure Map & AngularJs.

747 Total Views 1 Views Today
Mocking the objects

Leave a Comment

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>