Technology Corner

Home » DotNet » Unit Testing with Rhino Mock .Net

Unit Testing with Rhino Mock .Net

Enter your email address to follow this blog and receive notifications of new posts by email.

Join 80 other followers

Twitter updates

Error: Twitter did not respond. Please wait a few minutes and refresh this page.

Archives

RSS InfoQ Feeds

  • How Google Develops New Managers
    Alex Langshur, host of Google Partners Podcasts, has organized the podcast Google HR secrets: identifying & developing great managers, interviewing Sarah Calderon, People Development at Google, on how Google selects, trains, and develops their managers. By Abel Avram
  • Presentation: Cognitive Services, Next Step in Creating Our Robot Overlords
    Harold Pulcher discusses Cognitive Services, how to get started using them, and how to incorporate speech, image, and facial recognition into an application. By Harold Pulcher
  • Presentation: Control Flow Integrity Using Hardware Counters
    Jamie Butler and Cody Pierce discuss a new system for early detection and prevention of unknown exploits. Their system uses Performance Monitoring Unit hardware to enforce coarse-grained Control Flow Integrity (CFI). They intend to prove that their approach is effective and suitable for practical use, while staying resistant to bypass. By Jamie Butler
  • JetBrains Launches GoLand Go IDE
    JetBrains has moved its Go IDE from its early access programme to market. Now branded as GoLand, the IDE extends the IntelliJ platform making its core functionality specific to Go. This follows suit with their other language-specific tools such as PyCharm for Python and RubyMine for Ruby. By Andrew Morgan
  • Panel on the Future of AI
    An SF QCon panel on the future of AI explored some issues facing machine learning today. The areas explored: critical issues facing AI right now, how has technology changed the way people are hired, how non-leading edge companies make the best use of current technologies, what the role of humans in relation to AI is, and exciting new breakthroughs on the imm […]
  • Microsoft Updates Cosmos DB with Cassandra Support and Provides Better Availability Guarantees
    Last month at Microsoft Connect 2017, Azure Cosmos DB received several new updates, including support for using the Cassandra NoSQL database API and increased guarantees for availability. With the Cassandra NoSQL database API, customers can run operations inside Cosmos DB on a data model. The availability guarantee moves from 99.99 percent to 99.999 percent. […]
  • Article: Approximate Computing on WSO2: Explaining Approximation Algorithms in an Applied Setting
    In this article, we describe an example real world application of API monitoring which gets benefit by using approximate stream processing. We developed the application on top of WSO2 Stream Processor as Siddhi extension. Siddhi is the complex event processing library which acts as the event processing engine of WSO2 Stream Processor. By Chamod Samarajeewa
  • Rust in Visual Studio and VS Code
    Daniel Griffen has released a preview version of a Rust language service for Visual Studio. This plugin requires Visual Studio 2017 Preview, an experimental release stream for testing new VS features. By Jonathan Allen
  • Article: Key Takeaway Points and Lessons Learned from QCon San Francisco 2017
    The eleventh annual QCon San Francisco was the biggest yet, bringing together over 1,800 team leads, architects, project managers, and engineering directors. By Abel Avram
  • Article: Q&A With Eberhard Wolff On the Book “A Practical Guide to Continuous Delivery”
    Eberhard Wolff speaks with InfoQ about his work "Continuous Delivery: A Practical Guide", where we detail some of the major concepts behind successful CD adoption and the ripple-effect it can have on developer productivity and quality of service. By Dylan Raithel

I am covering unit testing with mock objects using Rhino mock .net library.

What is unit Test?

It is a method of testing a smallest unit of source code. Unit can be function or method. Unit tests are created during development process by developers or occasionally white box testers. Ideally each test case should be independent from each others. Unit tests helps to maintain quality of your application, it helps to find out any error or discrepancy during development process. There are many libraries available to unit test source code like nunit, mbunit, junit, MSTest etc.

What is mock object?

  • The mock objects are proxy of real objects which mimic behavior of real objects. Mock objects are mainly used in testing when testing with real objects is impractical or impossible to incorporate in unit testing. Below is some characteristics that can help you to decide to use mock objects.
    • Testing data is dynamic i.e. testing results cannot be determine on every test.
    • Unit testing includes network or database dependencies.
    • You don’t know about behavior of dependent objects.
  • Mock objects in this sense do a little more: their method implementations contain assertions of their own. This means that a true mock, in this sense, will examine the context of each call— perhaps checking the order in which its methods are called, perhaps performing tests on the data passed into the method calls as arguments.

What is Rhino Mock?

It is a dynamic mock object framework for the .Net platform. It includes features from EasyMock.Net and NMock. Below is some features of this library:

  • It can mock interfaces, delegates and classes including parameterized constructors.
  • Explicit Record & replay model for expectations.
  • Can work for strong type mock objects.
  • Expectations are based on
  • Argument matching.
  • Constraints matching.
  • Custom callback to verify the expected arguments using your own code.
  • Setting actions of methods, properties to return pre determine value.
  • you can also tests methods which doesn’t return any value. In this case you can test interaction based testing ie. you can verify specific sequence of actions and then you can verify these actions according to predefined order.
  • State base Testing: initiate action and then check  expected results.

Rules for using Rhino Mock

  • Rhino mock can only mock interfaces, delegates and virtual methods.
  • Mock objects cannot be created from sealed class.
  • Mock Objects cannot be create from private interface.

Examples of Rhino Mock

Expect Call

To create any mock object you need to create instance of MockRepository Class which act as project presenter.

I am taking very simple example how to create mock object and set expectation on property.

[TestMethod] 

public void TestMethod2() 
{ 
	//Testing with Mock Object 
    MockRepository repo = new MockRepository(); 
    TestClassForMockTesting obj = repo.CreateMock(); 
    Expect.Call(obj.Message).Return("hello"); 
    repo.ReplayAll();
    Assert.AreEqual("hello", obj.Message); 
    repo.VerifyAll(); 
}
public class TestClassForMockTesting
{
    public TestClassForMockTesting() { }
    public string Message
    {
        get
        {
            return Guid.NewGuid().ToString();
        }
    }
}

Output

Above code will raise exception : "Invalid call, the last call has been used or no call has been made (make sure that you are calling a virtual (C#) / Overridable (VB) method)." because any expect call can only set values for Virtual methods or properties. If you make Messageproperty as virtual then mock framework will set Message value as “Hello” instead on GUID which can’t be predicated on every call. if you do same test with real object it will always because you can’t return values.So if we make Message property as Virtual this test will pass.

public virtual string Message { get { return Guid.NewGuid().ToString(); } } 

Expect call for DbConnection and void method

this example test dbconnection open method. First we create mock dbconnection and inject dbconnection object through constructor as we know that without database connection string real database connection object will raise exception on calling Open method.On thing note here to expect call void method we have to use anonymous delegate in Expect.Call method.

[TestMethod]
public void TestDbConnection()
{
	//Testing with Mock Object
	MockRepository repo = new MockRepository();
	IDbConnection mockConn = repo.CreateMock();
	TestClassForMockTesting obj = repo.CreateMock(mockConn);
	//Expecting void methods
	Expect.Call(delegate { mockConn.Open(); });
	repo.ReplayAll();
	Assert.IsTrue(obj.openConnection());
	repo.VerifyAll();
}
public class TestClassForMockTesting
{
    public TestClassForMockTesting()
    {
    }
    //constructor for injecting Mock DbConnection
    public TestClassForMockTesting(IDbConnection conn)
    {
        _conn = conn;
    }
    IDbConnection _conn;
    public virtual string Message { get { return Guid.NewGuid().ToString(); } }
    public bool openConnection()
    {
        try
        {
            _conn.Open();
            return true;
        }
        catch (Exception ex)
        {
            return false;
        }
    }
}

If you don’t call this statement Expect.Call(delegate { mockConn.Open(); }) test will fail and will give error like

image

Test DataAccess Layer’s Method

This example shows how can we mock database connection and test our unit test. Expect.Call(obj.GetHotel(2)).Return(h).Repeat.Twice() this line tells same expectation twice because obj.GetHotel(2) statement is using two times.

public void TestGetHotels()
{
	 //Testing with Mock Object
	 MockRepository repo = new MockRepository();
	 IDbConnection mockConn = repo.CreateMock();
	 ITestClassForMockTesting obj = repo.CreateMock();
	 obj.DBConn = mockConn;
	 //Expecting void methods
	 Hotel h = new Hotel();
	 h.Name = "Taj";
	 h.Id = 3;
	 
	 Expect.Call(obj.GetHotel(2)).Return(h).Repeat.Twice();

	 repo.ReplayAll();
	 Assert.AreEqual("Taj", obj.GetHotel(2).Name);
	 Assert.AreEqual(3, obj.GetHotel(2).Id);
	 
	 repo.VerifyAll();
 }
public class TestClassForMockTesting : MyVacations.Tests.ITestClassForMockTesting
{
    public TestClassForMockTesting()
    {

    }
    public IDbConnection DBConn { set { _conn = value; } }
    //constructor for injecting Mock DbConnection
    
    IDbConnection _conn;
    public virtual string Message { get { return Guid.NewGuid().ToString(); } }
    public bool openConnection()
    {
        try
        {
            _conn.Open();
            return true;
        }
        catch (Exception ex)
        {
            return false;
        }

    }

    public Hotel GetHotel(int hotelId)
    {
        List lst = new List();
        DataSet ds = new DataSet();
        IDbDataAdapter odp = new SqlDataAdapter();
        IDbCommand cmd = new SqlCommand("select * from hotel where hotelid =" + hotelId.ToString());

        odp.SelectCommand = cmd;
        odp.SelectCommand.Connection = _conn;
        odp.Fill(ds);
        DataRow row = ds.Tables[0].Rows[0];

        Hotel h = new Hotel();
        h.Id = Convert.ToInt32(row["Id"]);
        h.Name = row["Name"].ToString();
        
        return h;
    }
}

References: http://www.ayende.com/wiki/Rhino+Mocks+Documentation.ashx

Syntax Examples: http://www.ayende.com/wiki/GetFile.aspx?File=Rhino+Mocks+3.3+Quick+Reference.pdf

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Blogs I Follow

%d bloggers like this: