Tuesday, July 21, 2020

xUnit walkthrough

There are three popular unit test frameworks for Visual Studio - nUnit, MSTest, and xUnit. I've never looked at xUnit before, but people seem to be trending towards it. To be honest, there doesn't seem to be much daylight between the three frameworks, but I do like the syntax of xUnit slightly better.

Let's walk through an implementation of xUnit using the Visual Studio runner (test container) because, quite frankly, the console runner is a joke.

Start a new Visual Studio class library project. I'm using 2019, C#, and the .Net Framework. Call the project ClassXUnit.

We need to add xUnit and the Visual Studio xUnit runner. Open the NuGet manager (Tools -> NuGet Package Manager -> Manage NuGet Packages for Solution), select Browse, and Search for and Install xunit.


Repeat for xunit.runner.visualstudio.

We will create a static class called Arithmetic with a single method called Add. Note the methods must have enough scope for us to call them from the test classes. It doesn't have to be a static class, but a non-static Arithmetic class makes no sense.


namespace ClassXUnit
{
    public static class Arithmetic
    {
        public static int Add(int a1, int a2)
        {
            return a1 + a2;
        }
    }
}

Unit tests take two forms [Fact] or [Theory]. A [Fact] test always runs exactly the same way. For example...


    public class TestArithmetic
    {
        [Fact]
        public void AddTest1()
        {
            Assert.Equal(4, Arithmetic.Add(2, 2));
        }
    }


Right-click on the solution and select "Run Tests". This opens the Test Explorer which will run all the tests (one so far) and tell us if the asserts passed or failed. You can drill down to see why a test failed, which we will do later.


Break the Add method so the assert fails...

             return a1 - a2;

and run the test again.


Fix the add method and run the test again to make sure it's working now.

The [Theory] tests are very useful. They allow you to run the same test repeatedly with different parameters. Add this to the TestArithmetic class.


        [Theory]
        [InlineData(2, 2, 4)]
        [InlineData(2, -1, 1)]
        [InlineData(2, -3, -1)]
        [InlineData(2, -2, 0)]
        public void AddTest2(int a1, int a2, int s)
        {
            Assert.Equal(s, Arithmetic.Add(a1, a2));
        }


You can see that AddTest2 will be called once for each [InlineData] with the specified set of parameters. This is a very powerful feature. The result is...


If we break the Add method by multiplying instead of adding, we can see the value of multiple tests with different parameters because some of the tests pass and some do not.

            return a1 * a2;






No comments:

Post a Comment