How to do integration testing in ASP.Net Core

Take advantage of xUnit and ASP.Net Core’s test host package to run integration tests on your ASP.Net Core web applications

How to do integration testing in ASP.Net Core
Thinkstock

Testing is an essential part of developing any application. There are various types of tests. Unit tests are used to check if the output of blocks or units of code conforms to the desired results. Integration tests are used to check if the different parts of the application work as expected when they are assembled together. In this article I will discuss how we can write and execute integration tests using ASP.Net Core.

Create a new ASP.Net Core project

First off, let’s create an ASP.Net Core project in Visual Studio. Assuming that .Net Core is already installed on your system, follow these steps to create an ASP.Net Core application in Visual Studio 2017.

  1. In the Visual Studio IDE, click on File > New > Project.
  2. Select “ASP.Net Core Web Application (.Net Core)” from the list of the templates displayed.
  3. Specify a name for the project.
  4. Click OK to save the project.
  5. In the “New .Net Core Web Application…” window, select “Web API.”
  6. Ensure that “Enable Docker Support” is unchecked.
  7. Select “No Authentication” as we won’t be using authentication in this example
  8. Click OK.

A new ASP.Net Core project will then be created with an example Controller to build and execute RESTful HTTP services.

Next, create a simple controller named DefaultController and enter the following code.

 [Produces(“application/json”)]
    [Route(“api/Default”)]
    public class DefaultController : Controller
    {
        // GET: api/Default
        [HttpGet]
        public string Get()
        {
            return “Hello World!”;
        }       
    }

Now that we have our controller, we’re ready to dive in. We’ll look at how we can write integration tests for this controller in the next section.

Create an xUnit test project in ASP.Net Core

Unit testing using xUnit, Moq, and Fluent Assertions is both useful and fun, and the newer versions of .Net Core support them. In this example, we’ll take advantage of xUnit. Now that our ASP.Net Core Web project has been created, let’s create a test project to write our integration tests. The first step is to create a unit test project, by following these steps.

  1. In the Visual Studio IDE, click on File > New > Project.
  2. Select “.NET Core” from the list of installed templates.
  3. Select “xUnit Test Project (.Net Core)” from the list of the templates displayed to the right.
  4. Specify a name for the project.
  5. Click OK to save.

This will create a unit test project and a default test file. Next, rename this default test file to DefaultTests.cs. To unit test your Web API methods, you should have a web server running. If you have your web and test projects in the same solution, you will typically want to invoke two instances of Visual Studio and run each project in a separate instance. Here’s exactly where a test server comes to the rescue.

Install the test host in ASP.Net Core

ASP.Net Core includes a handy test host that you can add to your integration test projects via NuGet. To install this test host package, select the integration test project in the Solution Explorer window, then right click and select “Manage NuGet Packages...” Then click “Browse,” search for the Microsoft.AspNetCore.TestHost package, and install it.

The following code snippet shows how you can create an instance of TestServer and use it to create an instance of HttpClient.

  public class DefaultTests
{
        private readonly TestServer testServer;
        private readonly HttpClient httpClient;
        public DefaultTests()
        {
            testServer = new TestServer(new WebHostBuilder()
            .UseStartup<Startup>());
            httpClient = testServer.CreateClient();
        }
}

Use the .Net Core TestServer to run the xUnit test method

The code snippet given below shows how you can use the TestServer to run your unit test method. Here the GetMessageTest unit test method reads a string asynchronously and then checks to see if the string object is null.

[Fact]
  public async void GetMessageTest()
        {
            var response = await httpClient.GetAsync(“http://localhost:45660/api/default”);
            response.EnsureSuccessStatusCode();
            var result = await response.Content.ReadAsStringAsync();
            Assert.NotNull(result);
        }

And here is the complete DefaultTests test class for your reference.

  public class DefaultTests
    {
        private readonly TestServer testServer;
        private readonly HttpClient httpClient;
        public DefaultTests()
        {
            testServer = new TestServer(new WebHostBuilder()
            .UseStartup<Startup>());
            httpClient = testServer.CreateClient();
        }

        [Fact]
        public async void GetMessageTest()
        {
            var response = await httpClient.GetAsync(“http://localhost:45660/api/default”);
            response.EnsureSuccessStatusCode();
            var result = await response.Content.ReadAsStringAsync();
            Assert.NotNull(result);
        }
    }

Note that it is good practice to isolate the unit tests and integration tests of your application. The reason is that while unit tests often use fakes and mocks, integration tests often need to incorporate the infrastructure concerns, i.e., database resources, file system resources, web requests and responses, etc. Also, you should aim to write fewer integration tests than unit tests as integration tests tend to run much longer. Don’t use an integration test when a unit test will do. 

Copyright © 2018 IDG Communications, Inc.