1

Прежде всего, я прочел этот похожий вопрос: Nested/Child TransactionScope Rollback, но ответ не дал решения, и наши вопросы немного отличаются.C# Rollback Outer TransactionScope Независимо от того, что происходит во вложенных транзакционных камерах

В принципе, у меня есть тест интеграции базы данных, которая использует объем транзакций (В действительности сфера управляются в установке/демонтаж в абстрактном классе)

[Test] 
public void MyTest() 
{ 
    using(var outerScope = new TransactionScope()) 
    { 
     Assert.True(_myService.MyMethod()); 
     var values = _myService.AnotherMethod(); 
    } 
} 

И MyService.MyMethod также использует TransactionScope

Так как теоретически MyMethod только фиксирует свои изменения, если isCheck является истинным, но независимо от того, совершает ли эта транзакция или нет, когда этот метод будет протестирован, он будет откат.

Он работает, как ожидается, если isCheck не является ложным, и в этом случае я получаю следующее исключение: System.Transactions.TransactionException : The operation is not valid for the state of the transaction.

Я думаю, что здесь произошло, что с innerScope использовали TransactionScopeOption.Required, он присоединился к транзакции, используемой в outerScope. После того, как innerScope будет удален, когда isCheck is false, также будет нарушен внешнийScope (это то, чего я не хочу!), Поэтому, когда я пытаюсь получить другое соединение после вызова MyMethod, внешний космос уже удален.

В качестве альтернативы, если я указываю TransactionOption.RequiresNew, я получаю это исключение: System.Data.SqlClient.SqlException : Timeout expired.

Я попытался с помощью SqlTransaction с определенной точки сохранения, а также различные комбинации TransactionOption не дало никаких результатов.

ответ

2

Вложенных транзакций не существует. Вы можете вложить области, но все, что вложенные области делают, - это прикрепить уже запущенную транзакцию. Вы не можете рассматривать внутреннюю область независимо от другой области (за исключением, конечно, RequiresNew, которая просто создает независимую транзакцию).

Функциональность, которой вы хотите, не существует в System.Transactions.

Savepoints - единственный способ создать что-то похожее на вложенные транзакции. Но опять же SQL Server склонен убить всю транзакцию по произвольным причинам. Непредсказуемо, какие ошибки отбрасывают заявление и какие ошибки откатывают транзакцию. (Да, это не имеет смысла.)