Iâ€™m curious if anyone has gone down the road of transactional integration testing with aspnet and ef core? I want to be able to perform full integration tests all the way to the db (not using an in-memory db). There are 2 problems:
I would like to wrap tests in a transaction (
_dbContext.Database.BeginTransactionAsync()). The problem is the DbContext I get from:
_server = new TestServer(builder); _services = _server.Host.Services; _dbContext = (AppDbContext)_services.GetService(typeof(AppDbContext))
Will be in a different scope (so a different instance) than the one that gets resolved by the AspNetCore middleware. So, only the test code would be transactional, not any code executed by the
TestServer. I have considered using some test middleware in a
TestStartup class that would wrap the API code in a transaction, but the problem there is it will be disposed/rolled back before the test can evaluate it. Consider the following use case:
In this case, the test needs access to the same dbContext instance used by the test server.
I tried a few hacky ways of passing the context using
AsyncLocal which didnâ€™t work so then I just tried using a simple
But, that also didnâ€™t work, so it appears there is some AppDomain isolation between the test app and the
Iâ€™m curious if anyone has gone down this road and if so, what they came up with?
Just closing out this issue. The solution was to register the DbContext as a singleton in the test startup class. So, in tests:
But, in the application it would be registered as:
A more complete answer has been posted here http://nance.io/leveling-up-your-dotnet-testing-transactional-integration-testing-in-asp-net-core/