.net 核心集成测试解析作用域服务
.net core integration tests resolve scoped services
我的集成测试很简单。我调用创建应用程序API,然后检查应用程序记录是否正确插入。
这是我的 CustomWebApplicationFactory:
public class CustomWebApplicationFactory<TStartup> : WebApplicationFactory<Startup>
{
public CustomWebApplicationFactory()
{
Configuration = new ConfigurationBuilder()
.SetBasePath(Directory.GetCurrentDirectory())
.AddJsonFile($"appsettings.{CustomEnvironments.IntegrationTests}.json", optional: true)
.AddEnvironmentVariables()
.Build();
Log.Logger = new LoggerConfiguration().ReadFrom.Configuration(Configuration).CreateLogger();
Log.Information("Starting integration tests");
}
protected override IHostBuilder CreateHostBuilder() =>
base.CreateHostBuilder()
.UseEnvironment(CustomEnvironments.IntegrationTests)
.UseSerilog();
}
这是我的 ApplicationControllerTests class:
public class ApplicationControllerTests : IClassFixture<CustomWebApplicationFactory<Startup>>
{
private readonly HttpClient _client;
private readonly MyDbContext _db;
private readonly CustomWebApplicationFactory<Startup> _factory;
public ApplicationControllerTests(
CustomWebApplicationFactory<Startup> factory)
{
_factory = factory;
_client = factory.CreateClient();
_db = factory.Services.GetRequiredService<MyDbContext>();
}
[Fact]
public async Task CreateApplication_WhenCalled_ShouldReturnSuccess()
{
var request = new CreateApplicationRequest
{
Name = "App1"
}
var response = await _client.PostAsync("/api/v1/Application/CreateApplicationForLive", request.ToJsonStringContent());
response.EnsureSuccess();
var applicationId = await response.Deserialize<Guid>();
var application = _db.Set<Application>().Find(applicationId);
Assert.Equal(request.Name, application.Name);
}
}
但是当我尝试解析 MyDbContext 范围内的服务时 _db = factory.Services.GetRequiredService<MyDbContext>();
我收到以下错误:
'Cannot resolve scoped service from root provider.'
从 WebApplicationFactory 获取作用域服务的正确方法是什么?我无法从文档 Integration tests in asp.net core
中找到任何示例
在 WebApplicationFactory 中解析作用域服务的正确方法是创建作用域:
var scope = factory.Services.GetRequiredService<IServiceScopeFactory>().CreateScope();
_db = scope.ServiceProvider.GetRequiredService<MyDbContext>();
我的集成测试很简单。我调用创建应用程序API,然后检查应用程序记录是否正确插入。
这是我的 CustomWebApplicationFactory:
public class CustomWebApplicationFactory<TStartup> : WebApplicationFactory<Startup>
{
public CustomWebApplicationFactory()
{
Configuration = new ConfigurationBuilder()
.SetBasePath(Directory.GetCurrentDirectory())
.AddJsonFile($"appsettings.{CustomEnvironments.IntegrationTests}.json", optional: true)
.AddEnvironmentVariables()
.Build();
Log.Logger = new LoggerConfiguration().ReadFrom.Configuration(Configuration).CreateLogger();
Log.Information("Starting integration tests");
}
protected override IHostBuilder CreateHostBuilder() =>
base.CreateHostBuilder()
.UseEnvironment(CustomEnvironments.IntegrationTests)
.UseSerilog();
}
这是我的 ApplicationControllerTests class:
public class ApplicationControllerTests : IClassFixture<CustomWebApplicationFactory<Startup>>
{
private readonly HttpClient _client;
private readonly MyDbContext _db;
private readonly CustomWebApplicationFactory<Startup> _factory;
public ApplicationControllerTests(
CustomWebApplicationFactory<Startup> factory)
{
_factory = factory;
_client = factory.CreateClient();
_db = factory.Services.GetRequiredService<MyDbContext>();
}
[Fact]
public async Task CreateApplication_WhenCalled_ShouldReturnSuccess()
{
var request = new CreateApplicationRequest
{
Name = "App1"
}
var response = await _client.PostAsync("/api/v1/Application/CreateApplicationForLive", request.ToJsonStringContent());
response.EnsureSuccess();
var applicationId = await response.Deserialize<Guid>();
var application = _db.Set<Application>().Find(applicationId);
Assert.Equal(request.Name, application.Name);
}
}
但是当我尝试解析 MyDbContext 范围内的服务时 _db = factory.Services.GetRequiredService<MyDbContext>();
我收到以下错误:
'Cannot resolve scoped service from root provider.'
从 WebApplicationFactory 获取作用域服务的正确方法是什么?我无法从文档 Integration tests in asp.net core
中找到任何示例在 WebApplicationFactory 中解析作用域服务的正确方法是创建作用域:
var scope = factory.Services.GetRequiredService<IServiceScopeFactory>().CreateScope();
_db = scope.ServiceProvider.GetRequiredService<MyDbContext>();