ShaneKm
ShaneKm

Reputation: 21308

Unit tests and mocking for each test

Sometimes in my test I need to perform a different Setup() call that sets up Mocks differently for each test run - like so:

private void Setup(bool isTrue)
{
    mock.Setup(x => x.DisplayNames).Returns(new Dictionary<int, string>());
    // ...
    // 5x more of these are the same for all tests

    if (isTrue)
      mock.Setup(x => x.DisplayOld).Returns(isTrue);
      // 5x more of these parameterlized setups 
      ...
}

Now, in each of my unit tests I would make a call to Setup(true/false).

Since unit tests are running in parallel (xUnit by default), will this cause any locking issues? (Suppose two tests call Setup() at the same time).

If that is the case:

  1. how to rectify this situation?
  2. what is the proper approach if one wants to have a single method (like setup()) with a parameter passed - for different mocking scenarios?

Upvotes: 1

Views: 2311

Answers (2)

Ivan Gerken
Ivan Gerken

Reputation: 914

Check the article about the Test Context pattern. You can have mocks as local variables and customize their setup in the test context class. Then it's safe to run them in parallel. I use this pattern in Java with JUnit+Mockito and in .Net with NUnit/MSTest+Moq.

Upvotes: 1

Jimmy
Jimmy

Reputation: 113

You need to use the parameterized unit testing. InlineData attribute of xUnit test framework can be used. The mock doesn't need to be set in the setup method in this case. It can be set directly in the actual test method. Your test method would look like below

[Theory]
[InlineData(false)]
[InlineData(true)]
public void SampleTest(bool flag)
{
    .... //do any set up operations
    .... //Assert logic to verify
}

The test framework will generate as many test methods at run-time based on the input you provide with the InlineData attribute. Since the test method is split into separate methods at run-time, you would not get into any locking or threading issues.

Upvotes: 0

Related Questions