How isolated are your tests and are they truly unit tests? Perhaps you've fallen into the pitfall of having several God Objects within your code and now you just have integration tests. It might be time to start using Moq, the easy-to-implement mocking library, ubiquitously used within Microsoft Docs for .NET. Moq can help ensure that your units under test have the same state as your application, and even make it easier to enforce shared test structure, such as through the Arrange, Act, Assert (AAA) model. It can help you write tests that are in complete control of the functionality and expectations, where the test adheres to the design pattern of dependency injection and the principle of inversion of control (IOC). Stop focusing your tests on the set up of your context, and instead come with me and learn about how to make your testing code even better.

What are Mocking and Moq?

The process of mocking, in software testing terms, involves creating dummy objects based upon your application's real objects and then using those dummy objects to simulate the behavior of your real objects in various conditions. It allows you to mimic dependencies that your code may have, allowing you to control their behavior in order to better test the functionality of the object you are testing. Mocking also allows you to ensure that a specific method was run with the expected parameters, or enforce that certain methods are only invoked the number of times you are expecting. These mocks can be as simple as faking a virtual method or as complex as ensuring that a call to your database was executed as expected. For this article, I'll be keeping things simple and the examples to the point.

I'm sure you're already thinking of specific situations in your tests where this could be incredibly helpful. Allow me to introduce you to the .NET-flavored mocking library Moq (sometimes also referred to as MOQ, but given that the acronym for MOQ has nothing to do with code mocking, it's generally written to use the initial capped version Moq). This library is freely available on GitHub (https://github.com/moq/moq4) and NuGet (https://www.nuget.org/packages/Moq), fully featured so there's no light version, and makes full use of .NET LINQ expression trees and lambda expressions. Unlike some other mocking library alternatives, Moq is type-safe and enforces that it's setting up expectations on your exact methods, and, where possible, not only relying on strings. When using Moq, you initialize the Mock object with your given interface (interfaces being the primary object you should be mocking) or class (which can be used, too, but results are not as good as for an interface), and then are ready to start mocking the behavior of your code.

Why Should I Use Moq?

There is no doubt that using Moq will help you create better software, particularly at the Enterprise level. Moq's fluent interface allows you to specify the expected behavior of your mock objects in a simple and readable way, which sets it apart from other alternatives, all while ensuring that you're developing loosely coupled software. By loose coupling, I am, of course, referring to using the dependency injection design pattern, so that you don't end up with classes that are dependent on each other. Moq works at its best when used in conjunction with dependency injection, and through its use, it can help to ensure that you don't end up with units of functionality that are each entirely responsible for creation and management of any number of instances. Instead, dependencies are injected into the code, so that a given class or method can focus on doing the functionality for which it was created. Arranging your code using dependency injection results in more modular code that is easier to test, easier to read, and a breeze to extend upon.

To tackle this from the direction of why you should use Moq specifically, when you could just create your own dummy objects, I provide this response (which is true for any library you might make use of for any coding language): to make your life easier. Why reinvent the wheel, as it were, and add code to your solution that won't be published as part of your application? Take full advantage of Moq, this free-to-use tool, and elevate your unit tests.

Key Areas of Unit Testing that Moq Can Help With

Like many other developers, I like to structure my unit tests using the AAA model. I feel it keeps things simple by dividing each test into functionality segments, so that it's known what to expect from each, which is useful for when new developers join the code. Fortunately, Moq can help you with each of these sections during the set up of your objects themselves, through to setting expectations on the methods within your mocked object. At the point that you need to access your mocked object, or the mock itself from a mock created instance, Moq can help there, too. This is true, right through to verifying that your object worked as expected and leads to expected assertions..

How to Use Moq

Using the AAA unit testing structure, along with some simple examples, I'll now demonstrate how Moq can be used to create better tests. I've provided a simple example that will be consistently used all the way through so you can notice functionality all the way through development. Although not all of Moq's features will be demonstrated, I cover the most important parts, and cover anything else of note further down in the Other Moq Functionality section.

Installing and Using Moq

To start you off with the most basic of parts, you'll first need to add Moq to your project. As in Figure 1, with your project open, navigate to the Tools menu of Visual Studio, hover over NuGet Package Manager, and then select Package Manager Console.

Figure 1: Navigate to NuGet Package Manager, open the Tools menu, and then open the NuGet Package Manager option followed by Package Manager Console.
Figure 1: Navigate to NuGet Package Manager, open the Tools menu, and then open the NuGet Package Manager option followed by Package Manager Console.

With Package Manager Console open, click to ensure that your Package source is nuget.org, and that your Default project is the project where you wish to add Moq. In Figure 2, this is the ExampleProject.Library project. You're now free to install Moq. Simply click the command line interface so that the caret appears alongside PM>, type Install-Package Moq -Version 4.18.4, and press Enter. The package will be retrieved and installed, and you will likely see a bunch of text within the Package Manager Console. When the PM> shows once more, the installation has completed.

Figure       2      : The Package Manager Console, where you can install NuGet packages
Figure 2 : The Package Manager Console, where you can install NuGet packages

You can verify that Moq installed correctly by checking your Solution Explorer, opening your Dependencies list, and then opening Packages, as demonstrated in Figure 3.

Figure       3      : Moq can now be seen installed within your selected project.
Figure 3 : Moq can now be seen installed within your selected project.

You've successfully installed Moq and you're now ready to graduate to making use of it. The first step here is implementing the Moq Using statement. When you're mocking a class with a protected method or property - which is discussed at further length later in this article - you'll find that you also need to make use of the Protected Using statement. You can see both implemented in the code snippet below.

using Moq;
using Moq.Protected;

You can add these statements to either the global Using file or at the top of your testing file, whatever is most convenient for you. Note that the latter Protected Using statement must be provided as a declarative, and you can't provide it explicitly in-line because the library is inclusive of extension methods. It's time to dive into making use of the Moq library itself.

Arrange

Consider the next code snippet, which depicts a simple method for determining an employee's pay rate depending on the day of the week.

public decimal GetPayRate(decimal baseRate)
{
   return DateTime.Now.DayOfWeek == 
           DayOfWeek.Sunday ?
           baseRate * 1.25m :
           baseRate;
}

Usually, methods like this have to go untested or need to be changed so that a test can be created. The issue can be seen when looking at the test below, wherein the test is likely to fail because a different result will be produced depending on which day of the week it is. Creating tests with dependencies on static references, such as the DateTime.Now property, results in a test that doesn't have complete control of its context.

public void       
GetPayRate_IsSunday_ReturnsHigherRate_Snippet2()
{
          // Arrange
          var rateCalculator = new RateCalculator();

          // Act
          var actual = rateCalculator.GetPayRate(10.00m);

          // Assert
          Assert.That(actual, Is.EqualTo(12.5m));
}

Updating this to use abstraction, you can separate the fetching of the day of the week out to an interface and take greater control of the employee pay rate method, like the below code snippet. Through doing this, the interface can then be injected into the method, removing a dependency. This is an excellent modification that puts inversion of control on full display, as the method is now agnostic to its environment and context and will now singularly rely on what is passed into it.

public interface IDateTimeProvider
{
    DayOfWeek DayOfWeek();
}
public decimal GetPayRate(decimal baseRate,
    IDateTimeProvider dateTimeProvider)
{
          return dateTimeProvider.DayOfWeek() == 
                 DayOfWeek.Sunday ?
                 baseRate * 1.25m :
                 baseRate;
}

At this point, you'd expect to create a dummy class that makes use of the interface, so to override it and put back your result. Instead of that though, cut out that arbitrary code, and make use of Moq instead.

public void
GetPayRate_IsSunday_ReturnsHigherRate_Snippet4()
{
    // Arrange
    var rateCalculator = new RateCalculator();
    var dateTimeProviderMock =
        new Mock<IDateTimeProvider>();
    dateTimeProviderMock.Setup(m => m.DayOfWeek())
                        .Returns(DayOfWeek.Sunday);

    // Act
    var actual = rateCalculator.GetPayRate(10.00m,
        dateTimeProviderMock.Object);
          
    // Assert
    Assert.That(actual, Is.EqualTo(12.5m));
}

As in the code snippet above, you initialize the mocked object by passing in the interface to be mocked as part of the constructor. Moq dynamically creates a class of its own based upon the IDateTimeProvider interface, and fills in any implementations the interface may have.

You can then specify the Setup extension, which allows you to provide an expectation for when the DayOfWeek method is called, effectively overriding the method. As part of the setup, Moq uses the LINQ-like expression tree and lambda expression format to explicitly grab the method. Giving you access to the method means that, as a developer, you can see what parameters the method requires. You're also assured that the method you're attempting to set expectations on is truly mocked, right down to the specific method overloads.

Directly following the Setup extension, as seen in the above snippet, the Returns extension is then used. Moq doesn't require the use of a Return for a given setup, but for this example, let's make use of it as we're expecting a result from the method. The Returns extension is powerful, and it's possible to provide either an exact result (such as is the case for the above example), or a full expression, wherein you can make use of passed through parameters, and trigger any other code you may wish to run.

The result is not only a better test mechanism, but the code itself, while largely unaltered, can be manipulated and extended to a greater degree. When the test in the above code snippet is run, you can now be assured that the result will be the expected result, regardless of which day of the week it is.

Act

You have now seen how Moq can simplify your testing when arranging your objects, but as demonstrated within the previous code snippet, when a Mock instance is initialized, a mocked object is created that's simply flavored like your provided interface or class. To demonstrate how to access methods or properties directly from that mocked object, I've updated the previous interface, as seen in the following code snippet, so that it now contains a Name property.

public interface IDateTimeProvider
{
    DayOfWeek DayOfWeek();
    string Name { get; set; }
}

With this new interface in place, at the time when you need to access the object itself, Moq exposes an Object property as part of the dynamically created mocked class. This is demonstrated within the code snippet below, wherein the Name property can be accessed, and even set, directly through the mock.

// Arrange
var rateCalculator = new RateCalculator();
var dateTimeProviderMock = new Mock<IDateTimeProvider>();
dateTimeProviderMock.Setup(m => m.DayOfWeek()
                    .Returns(DayOfWeek.Sunday);
dateTimeProviderMock.Object.Name = "DateTimeProvide#1";

This is largely all you'll need for the Act sections of your tests when using Moq. Another option is the static Get method, as seen in the next code snippet, which allows you to access the mock wrapper on a given mocked object.

IExampleInterface foo =
    ExampleClass.ReturnedFromSomewhereElse();

var fooMock = Mock.Get(foo);
fooMock.Setup(m => m.DoNewAction()).Returns(false);

Assert.That(fooMock.Object.DoNewAction(), Is.EqualTo(false));

I don't tend to use this a lot, as altering the arrangement of a test at the point of acting upon it breaks the AAA structure, but it's reassuring to know that, in instances where you might be passed a mocked object from somewhere you can't control, you can still append to it.

Assert

The assertion section of AAA is where you ensure that a test ran as expected and you have the expected results. All good unit tests have an assertion, and I try to make it a rule that I only assert one thing in each of my unit tests. Having a single assertion leads to greater accuracy: Should something ever break when new features are added in the future, that developer will have an easy time of identifying the exact location of the break and what needs to be done to create a fix.

When unit testing, you generally have your tests checking the results of a called method, or code interaction, but what if you want to know what happened while your code was under test? Perhaps you want to know that a certain property was fetched a specific number of times, or to ensure that a certain method was not ran. For these cases, Moq gifts us with the verification functionality.

// Arrange
var rateCalculator = new RateCalculator();
var dateTimeProviderMock
          = new Mock<IDateTimeProvider>();
dateTimeProviderMock.Setup(m => m.DayOfWeek())
                    .Returns(DayOfWeek.Sunday);

// Act
var actual = rateCalculator.GetPayRate(10.00m,
                 dateTimeProviderMock.Object);
// Assert
Assert.That(actual, Is.EqualTo(12.5m));
dateTimeProviderMock.Verify(m => m.DayOfWeek(),
                                 Times.Once());

Building upon the previous code examples, you can see in the most recent snippet that there's a regular test set up for the IDateTimeProvider interface. Within it, you wish to know how many times the DayOfWeek method was called. You implement the Verify extension on the mock within the Assert section of the test. You also make use of Moq's static Times class, which provides various options for setting expectations for the number of times a method or property was called.

On display once more within the previous code snippet, is the readability benefit of Moq. Usage of the Times utility class results in tests that can be easily interpreted for their function: You have the mocked object and you wish to verify that it worked as expected, which you do by checking that the Setup method was called the number of times you expected it to run. Note, too, that there are some other possible usages of Times within the below code snippet, including Exactly, which specifies an expectation that several calls are made but no more or less than the given integer. Following the usage of Exactly is the Never method, which enforces that the given method or property was never called. There are several other options, but these are some of the more common you may run across while using Moq.

// This is expected to run exactly three (3) times
dateTimeProviderMock.Verify(m => m.DayOfWeek(), Times.Exactly(3));

// And this property should never run.
dateTimeProviderMock.Verify(m => m.Name, Times.Never());

Although you don't need to place a setup on a method to make use of the verify functionality, if you do add a setup, it's possible to make a general verification that your setup was run. By making use of Moq's VerifyAll method, as seen within the next code snippet, you can ensure that all setups that were placed on your mock were invoked.

// Arrange
var rateCalculator = new RateCalculator();
var dateTimeProviderMock = new
    Mock<IDateTimeProvider>();
dateTimeProviderMock.Setup(m => m.DayOfWeek())
                    .Returns(DayOfWeek.Sunday);
// Act
var actual = rateCalculator.GetPayRate(10.00m,
                 dateTimeProviderMock.Object);
// Assert
Assert.That(actual, Is.EqualTo(12.5m));
dateTimeProviderMock.VerifyAll();

Upon triggering the VerifyAll method when running your test, if any of your setups have not been invoked, an exception will be produced. This can be helpful if your called code is multifaceted and has several setups, each of which you require to be called.

The final verification functionality to showcase is the VerifyNoOtherCalls method, which does what it says it will do. As seen in the next code snippet, this method is placed after all other verifies, so that you can then enforce that there are no invocations on the mocked object from that point onward to any of its methods or properties.

// Arrange
var rateCalculator = new RateCalculator();
var dateTimeProviderMock = new Mock<IDateTimeProvider>();
dateTimeProviderMock.Setup(m => m.DayOfWeek())
                    .Returns(DayOfWeek.Sunday);

// Act
var actual = rateCalculator.GetPayRate(10.00m,
                 dateTimeProviderMock.Object);
// Assert
Assert.That(actual, Is.EqualTo(12.5m));
dateTimeProviderMock.Verify(m => m.DayOfWeek(),
                             Times.Exactly(1));
dateTimeProviderMock.VerifyNoOtherCalls();

If there are further invocations, an exception is produced, allowing you to hunt down the rogue calls and ensure that your code runs specifically as designed.

Other Moq Functionality

The functionality options for Moq are vast, so to keep things brief, only the most common functionality has been demonstrated so far. This section will give you a taste of some of the other possibilities, including parameter matching, throwing exceptions, accessing protected methods or properties, callbacks, and sequences.

Parameter Matching

When putting together a Setup or Verify for a method, Moq requires the provision of all parameters that method may take, including those that are optional. This ensures that you set up the correct expectation, as, due to the overloading functionality within C#, it's possible to select the wrong method. Within the below code snippet, you'll see that the method MyCalculatorMethod requires a string and a decimal.

mock.Setup(m => m.MyCalculatorMethod("HelloWorld!",
                                10.00m))
    .Returns(true);

mock.Setup(m => m.MyCalculatorMethod(It.IsAny<string>(), 
                                     It.IsAny<decimal>()))
    .Returns(true);

Providing specific parameters, such as “Provided Name” and “10.00m”, means that if a Verify is triggered after the Act segment, it expects that MyCalculatorMethod ran specifically with the provided parameters. This is helpful in ensuring that what you were expecting was indeed provided.

For the second usage within the code snippet, you'll see that it's also possible to provide stand-in values, for the times where you don't care what's passed in, just that those values were provided. To use this functionality, Moq provides the static library of It, where you can find the static method of IsAny<T> that allows you to simulate any given type. This functionality is incredibly helpful, as it works with custom types, too. For the times where you need to pass a reference-type through your method, Moq also provides the Ref<T> method as part of the It library.

Throwing Exceptions

Not all methods are meant to simply be expectations with returns, as at times you need to ensure that an exception is thrown when certain conditions are met. For these situations, as demonstrated in the following code snippet, Moq provides the Throws extension, which can be used in-place of the Returns method, following a Setup.

// Arrange
var mock = new Mock<IDateTimeProvider>();
mock.Setup(m => m.DayOfWeek())
    .Throws(new Exception());

// Act
var result = ExampleClass.MethodWhichMakesUseOfMock
    (mockedObject: mock.Object);

// Assert
Assert.That(result, Is.EqualTo(true));
mock.VerifyAll();

As you know, the benefit of having access to functionality like this means that you don't need to manually arrange some specific circumstance for the exception to be thrown, it just happens when the expected method is invoked. The structure used for the test in the code snippet involves the creation of an expectation, followed up with a Verify, to ensure that the exception was thrown. If the verify runs and the throw wasn't triggered, the test produces an exception.

Accessing Protected Setups

For the times when you're mocking a class and some of its functionality is protected, Moq provides the Moq.Protected library. The use of this means that the setup of your mocks is slightly different, as seen in the next code snippet, wherein the extension Protected is appended to the mock prior to the rest of the Setup.

// Arrange
var mock = new Mock<InheritingExample>();
mock.Protected()
    .Setup<bool>("MyProtectedMethod", 
                 "AStringToPassToThisMethod",
                 ItExpr.IsAny<string>())
    .Returns(true);

// Act
var result = mock.Object.AMethodWhichRunsTheProtectedMethod();

// Assert
Assert.That(result, Is.EqualTo(true));
mock.VerifyAll();

Structurally, the test is largely the same, meaning that there's still no doubt what this mock will be doing, and it still reads clearly. Now it also informs the developer that it will be working using a protected mocked object.

Protected functionality for Moq is implemented by providing the protected method's name as a string. Usage of this functionality comes at the cost of less explicit code and thus it's ideal that your code is structured around interfaces that mitigate this issue. Moq does provide the ability to mock classes and so the situation wherein you might need to access a protected method is possible. In these cases, albeit not being ideal, it's good to know that there are options for mocking.

Be aware that when using the protected version of a Setup, the It library works slightly differently. Instead of It, you'll need to use ItExpr. This provides the same functionality but it's labelled differently so that they don't conflict.

Callbacks

A powerhouse of a method, Callback allows the provision of a provided action that should be run when an expectation is invoked. Callbacks, as demonstrated in the next code snippet, can be helpful for many reasons, such as setting shared objects or running the save operation after a mocked method has been triggered.

// Arrange
var values = new bool[] { false, false, false };
var mock = new Mock<IExampleInterface>();
mock.Setup(m => m.DoNewAction())
    .Callback(() => values[0] = true)
    .Returns(true)
    .Callback(() => values[1] = true);

// Act
values[2] = mock.Object.DoNewAction();

// Assert
Assert.That(values.All(x => x == true),
    Is.EqualTo(true));
mock.VerifyAll();

As demonstrated, the structure for using Callback is similar to Returns and Throws, keeping usage of the extensions consistent. Additionally, Callback can be used alongside these other extensions, such as by stacking them so that code is run before and after an invocation.

Sequences

What about the times you expect a method to be called three times, each with different results? You're looking for Moq's SetupSequence method, which can be used in-place of the Setup method. As seen in the following code snippet, it's possible to stack your mock with several expectations that you're expecting to happen in a set sequence order.

// Arrange
var mock = new Mock<IDateTimeProvider>();
mock.SetupSequence(m => m.DayOfWeek())
    .Returns(DayOfWeek.Sunday)
    .Returns(DayOfWeek.Tuesday)
    .Returns(DayOfWeek.Saturday);

// Act
var result = 
    ExampleClass.ChecksSequenceIsCorrect(
        mockedObject: mock.Object);

// Assert
Assert.That(result, Is.EqualTo(true));
mock.VerifyAll();

Extensions can be stacked, so include Returns, Callback, or Throws as necessary, extending further the possibilities for testing various scenarios. For the above code example, the first return will be Sunday, the second Tuesday, and the last Saturday.

The Advantages of Using Moq Over Other Libraries?

If a project lends itself to mocking, such as by having complex objects or tests that could be improved by using mocking, any mocking library is a positive. For me, mocking helps enforce better structure and thoughtful design for my interfaces and classes. I more frequently use dependency injection when I also use Moq, and now, looking back at older projects where I've used Moq, I find that I can quickly and easily get back into development, as the structure of my tests guides my understanding of the functionality I created previously.

There are several alternatives to Moq, including NSubstitute, FakeItEasy, Rhino Mocks, and EasyMock, each with strengths and weaknesses. One of the biggest advantages of Moq by comparison, which you will have seen on full display, is its simple and intuitive syntax. Creating and setting up mocked objects is not only easy, but incredibly quick, which is made possible by Moq providing the expression tree structure and the ability to use it alongside lambda expressions. For developers who may not have used Moq, or mocking more generally, Moq provides a friendly library of functionality that will have most developers on their way quickly. As demonstrated, Moq's rich set of features and capabilities allow developers to create complex mocked objects and set up behavior in a wide range of testing scenarios. This makes it a versatile and powerful tool for C# .NET unit testing. Although Moq may not be as flexible or powerful as some of the other mocking libraries mentioned, its simplicity and ease of use make it a great choice for many developers.

Wrapping Up

Moq is a useful tool for improving the isolation and effectiveness of your unit tests. Transform your code by making use of mocking and enforcing patterns such as dependency injection and the principle of inversion of control. Through using Moq's easy-to-implement library, you can ensure that your units under test have the same state as your application, so that there are no more headaches from indecipherable and confusing dummy classes. I've provided several resources in Table 1 to continue your learning, including the Moq quick start guide and using Moq for events, should you wish to do so. Thank you for joining me on this adventure, and I hope that you're soon well on your way to implementing mocking within your code and making use of all that Moq can provide. And I'm certain that, through its use, the quality of your testing code will just get better and better.

Table 1: Resources and Further Reading

ResourceLink
Example Codehttps://github.com/elliotmoule/CODE.UsingMoq.Article.ExampleCode
Moq (GitHub)https://github.com/moq/moq4
Moq (NuGet)https://www.nuget.org/packages/Moq
Quickstart Guidehttps://github.com/Moq/moq4/wiki/Quickstart
Events (further reading)http://www.blackwasp.co.uk/MoqEvents.aspx