У меня есть метод, похожий на:
public async Task SaveItemsAsync(IEnumerable<MyItem> items)
{
using (var ts = new TransactionScope())
{
foreach (var item in items)
{
await _repository.SaveItemAsync(item);
}
await _repository.DoSomethingElse();
ts.Complete();
}
}
У этого, конечно, есть проблемы, потому что TransactionScope
не играет хорошо с async/await.
Сбой с сообщением:
"TransactionScope должен быть расположен в том же потоке, который был создан."
Я читал о TransactionScopeAsyncFlowOption
в этом ответе, который появляется быть тем, что мне нужно.
Однако для этого конкретного проекта у меня есть жесткое требование поддерживать .Net 4.0 и не может обновиться до 4.5 или 4.5.1. Таким образом, поведение async/wait в моем проекте предоставляется пакет Microsoft.Bcl.Async NuGet.
Я не могу найти TransactionScopeAsyncFlowOption
в этом или любом другом OOB-пакете. Я просто пропустил его где-то?
Если он недоступен, есть ли альтернатива для достижения того же результата? То есть, я хотел бы, чтобы область транзакций была должным образом завершена или откат, несмотря на пересечение потоков с продолжением.
Я добавил DoSomethingElse
в примере выше, чтобы проиллюстрировать, что в пределах транзакции может быть несколько вызовов, поэтому простое перенос всех элементов в базу данных одним вызовом не является жизнеспособным вариантом.
В случае, если это важно, репозиторий использует прямые ADO.Net(SqlConnection
, SqlCommand
и т.д.) для записи на SQL Server.
UPDATE
Я думал, что у меня есть решение, которое связано с использованием System.Transactions.dll из .Net 4.5.1 и включения его в мой проект. Тем не менее, я обнаружил, что это работало только в моей dev-блоке, потому что у него уже было установлено 4.5.1. Он не работал при развертывании на машине только с .Net 4.0. Он просто дал MissingMethodException
. Я ищу решение, которое будет работать с установкой .NET 4.0.