我们有大约 150 个并行运行的集成测试。为了确保它们是隔离的,我们每次都会创建一个新的数据库。要创建数据库,我们调用
DatabaseContext.Database.MigrateAsync()
。
不幸的是,每次额外的迁移都会增加设置数据库的时间。
我尝试过的替代方案并没有减少总时间:
EnsureCreated
.bacpac
文件恢复我唯一成功的就是删除所有现有的迁移并在其位置创建一个迁移。这显着缩短了总测试时间 - 最多可缩短 50%。但这感觉就像是黑客攻击,我不想添加一些额外的重复维护步骤。
创建新的测试数据库的最快方法是什么?
我找到了一种简单的方法来初始化数据库,而无需在每次迁移时进行调用:
private readonly WebApplicationFactory<Program> _factory;
public async Task InitializeAsync()
{
await using AsyncServiceScope scope = _factory.Services.CreateAsyncScope();
SampleDbContext dbContext = scope.ServiceProvider.GetRequiredService<SampleDbContext>();
// this is using types normally hidden to application code
IRelationalDatabaseCreator databaseCreator = dbContext.Database.GetService<IRelationalDatabaseCreator>();
// needed for idempotency if retrying this method due to transient errors
await databaseCreator.EnsureDeletedAsync();
// creates database without schema
await databaseCreator.CreateAsync();
// script is not idempotent nor executed in a transaction
string script = dbContext.Database.GenerateCreateScript().Replace("GO", "");
await dbContext.Database.ExecuteSqlRawAsync(script);
}
可以改进的地方: