3

分散トランザクションに参加する次の WCF サービスについて考えてみましょう。WCF の通常の動作は、障害が発生した場合にトランザクションをロールバックすることです。その動作をオーバーライドする方法はありますか?

サービス契約:

[ServiceContract]
public interface ITestService {
    [OperationContract]
    [FaultContract(typeof(TestServiceFault))]
    void ThrowError();
    [OperationContract]
    void DoSomething();
    [OperationContract]
    void DoSomethingElse();
}

[DataContract]
public class TestServiceFault{}

サービスの実装:

class TestService : ITestService {
    [OperationBehavior(TransactionScopeRequired = true)]
    [TransactionFlow(TransactionFlowOption.Mandatory)]
    public void ThrowError() {
        throw new FaultException<TestServiceFault>(new TestServiceFault());
    }
    [OperationBehavior(TransactionScopeRequired = true)]
    [TransactionFlow(TransactionFlowOption.Mandatory)]
    public void DoSomething() {
        //
        // ...
        //
    }
    [OperationBehavior(TransactionScopeRequired = true)]
    [TransactionFlow(TransactionFlowOption.Mandatory)]
    public void DoSomethingElse() {
        //
        // ...
        //
    }
}

クライアント実装スニペット:

using(new TransactionScope()) {
    testServiceClient.DoSomething();

    try {
        testServiceClient.ThrowError();
    } catch(FaultException<TestServiceFault>) {}

    testServiceClient.DoSomethingElse();
}

FaultException がThrowError()からスローされると、WCF は、 DoSomething()によって行われた作業を含む分散トランザクションをロールバックします。次に、DoSomethingElse()へのクライアント呼び出しが失敗し、 「フローされたトランザクションをアンマーシャリングできませんでした」というメッセージが表示されます。次の例外が発生しました: トランザクションは既に暗黙的または明示的にコミットまたは中止されています。

私の特定のシナリオでは、この動作は望ましくありません。クライアント側で例外をキャッチし、ビジネスを続行したいと思います。キャッチできない例外が発生した場合、クライアントはトランザクションをロールバックします。

注: この質問は、トランザクション全体を中止せずに WCF で FaultException を処理する方法の複製です。、しかし、受け入れられた答えは私にとって満足のいくものではありません-すべての操作が同じトランザクションスコープ内で発生することが重要です。

4

1 に答える 1

4

サービス側で TransactionAutoComplete=false を設定してから、 SetTransactionComplete() を使用して、例外が作業をロールバックしないようにすることができます。

于 2011-02-20T08:19:25.923 に答える