Я пытаюсь асинхронно добавить несколько объектов в свою базу данных в качестве «упорядочивающей» части моего интеграционного теста.
Однако я получаю двойные записи с исходным кодом:
private async Task<Foo[]> GenerateFoos(params string[] names)
{
var tasks = names.Select(async name =>
{
var foo = new Foo() { Name = name };
await AddAsync(foo);
return foo;
});
await Task.WhenAll(tasks);
return tasks.Select(task => task.Result).ToArray();
}
[Test]
public async Task MyTest()
{
var expected = await GenerateFoos("A", "B", "C");
}
Он генерирует вдвое больше объектов (по два каждого) в моей базе данных, и я не могу понять почему.
Я просмотрел другие примеры в Интернете, но все они предполагают, что Метод asyn c (AddAsync
в моем случае) возвращает объекты, которые я хочу вернуть, но здесь это не так; as AddAsync
возвращает только идентификатор, но я хочу вернуть сам добавленный объект.
Я дважды переработал код, и эти две альтернативы не вставляют дубликаты:
// Alternative 1
var result = new List<Corporation>();
foreach (var name in names)
{
var foo= new Foo() { Name = name };
await AddAsync(foo);
result.Add(foo);
}
return result.ToArray();
// Alternative 2
var foos = names.Select(name => new Foo{ Name = name });
await Task.WhenAll(foos.Select(foo => AddAsync(foo)));
return foos.ToArray();
Так что я почти уверен, что ошибка связана с моим кодом, а не с кодом AddAsync
. Но я не понимаю, почему первый ведет себя иначе. Хотя я не ожидаю, что содержимое AddAsync
имеет здесь значение, я добавляю его для завершения:
public static async Task AddAsync<TEntity>(TEntity entity)
where TEntity : class
{
using var scope = _scopeFactory.CreateScope();
var context = scope.ServiceProvider.GetService<MyDbContext>();
context.Add(entity);
await context.SaveChangesAsync();
}
Может ли кто-нибудь определить, почему мои задачи выполняются дважды?