Photo by Jeswin Thomas on Unsplash

How to setup and run Integration Tests with Azure Storage or Cosmos DB as dependencies on GitHub Action

David Lee

--

When we are doing local app development, we have tools such as Azurite for Azure Storage emulation or Cosmos DB Emulator we can install and run locally. Because of this, we don’t have to create an actual instance of Azure Storage or Cosmos DB instance on the cloud. When we run our integration tests locally, we are required to plugin in the connection strings to connect to our emulators and those connection strings are constants that don’t change.

Before we start looking at GitHub Action, let’s layout how we have written our integration tests. We will rely on configuration to determine the connection strings at runtime. As an example, with .NET, this means injecting IConfiguration into our Service class. Here’s a concrete example of a Service class taking a IConfiguration dependency and creating a client instance from the configuration.

As such, in our integration tests, we can make use of mocked interface instance to setup our connection strings. We will be using NSubstitute for easy mocking. The last point is that we will be using MSTest as the testing framework.

One particular thing to note here is that one line 9, we have hardcoded the connection string constant. When the Service code ask for TableStorageConnection string, we will return the constant connection string. The can be seen with the “Returns” keyword.

As part of the integration, we want to seed our database so we can test our business logic. With MSTest, we will use the TestInitialize attribute to make sure we run a seeding routine before every test and TestCleanup attribute to make sure we cleanup the database. This will ensure we have a known database state each time and ensure the deterministic nature of our tests.

As we commit and push code out, we will naturally need to use those same emulators. For our discussion today, we will be using GitHub Action for running our integration tests which brings us to the next part of our discussions.

Containerization is becoming a big part of the development process today. Instead of installing Azurite and Cosmos DB emulator locally, we can certainly use the container version if we have docker. For Azurite, we can use:

docker pull mcr.microsoft.com/azure-storage/azurite

And for Cosmos DB emulator, we can use:

docker pull mcr.microsoft.com/cosmosdb/linux/azure-cosmos-emulator

This means we don’t have to worry about having to manage the installation or any bits or files that may not be cleaned up on uninstall or updates. We simply remove the container if we don’t need it anymore, thus ensuring a clean development environment. With GitHub Action, you have the option of running those containers as part of the workflow as seen in this article here. However, it appears this is not support on Windows. Here’s an error you will see if you are running on Windows based runners.

Container operations are only supported on Linux runners

So the choice would be to configure your integration tests job to run on a linux runner which is a none-issue because we are using .NET 5 and it does not necessary need to run with a Window platform. However, at the time of this writing, the Linux Docker version of Cosmos DB emulator is still in preview. So, instead of trying it out, I decided to just look at using a traditional approach of just installing the emulators.

There is an existing GitHub Action someone has created for Cosmos DB: https://github.com/southpolesteve/cosmos-emulator-github-action. This means a simple one liner to install and use Cosmos DB emulator! At the time of this writing, it appears it has been a while since this was updated, so my thoughts are to use this for now until the Linux Docker version of Cosmos DB emulator is GA-ed. It will be interesting as a follow up article then!

For Azurite, we will use NPM to install and run it in the background using the following:

- run: npm install -g azurite- shell: bashrun: azurite-table &

Notice that we can selectively just run the Azure Table Storage endpoint using azurite-table — which is what our integration tests is using. If you are wondering what I am using Bash as my Shell, it appears this is the only way the table storage endpoint is visible. For more information, see this issue here.

Now that we have everything we need, to run the integration tests, it is a simple dotnet test command. However, we will need to do a few more work to publish out the results. If you have followed my previous article on this topic, you will know we need to use the following GitHub Action.

EnricoMi/publish-unit-test-result-action/composite@v1

The end result would be a nicely formatted visual that shows our test pass rate as well as any tests that failed as seen in the screenshot below.

A screenshot showing the integration test results.

That’s a wrap. As always, the source code of what we discussed can be found at: https://github.com/seekdavidlee/az-integration-tests-with-storage-and-cosmosdb. This is an actual working copy and I encourage you to fork it for your own review.

I do hope you have enjoyed this reading and learned something new today. I appreciate any feedback from you. Thank you!

--

--

David Lee
David Lee

Written by David Lee

Cloud Solution Architect/Software/DevOps Engineer

Responses (1)