0

System.Transaction.TransactionScopeを使用して、いくつかのストアドプロシージャを呼び出すトランザクションを作成しようとしていますが、それ自体がクリーンアップされていないようです。トランザクションが終了すると(コミットされているかどうかに関係なく、トランザクションスコープオブジェクトが破棄されると)、データベースへの後続の接続は、通常のように読み取りコミットではなく、シリアル化可能な読み取りコミットレベルで開きます。

呼び出しごとに接続を開いたり閉じたりします(.NETの通常のように接続のプールを閉じて戻る)、トランザクションでの使用が終了したときに接続を明示的にリセットする方法がありませんか?System.Transaction.TransactionScopeの背後にある考え方は、すべての複雑さを隠すことだと思いました。

したがって、私が持っているコードは次のようになります。

            using (var scope = new TransactionScope())
            {
                ... make my 3 stored procedure calls ...

                scope.Complete();

                return returnCode;
            }

これが通常の方法だと思います。しかし、sqlserverプロファイラーを見ると、接続が開かれていることがわかります。

set transaction isolation level serializable

これは、後続の非トランザクション関連のデータベースアクティビティを台無しにしており、明らかにそれほど高速ではありません。ReadCommitedを使用してトランザクションを明示的に実行するようにトランザクションオプションを設定することでこれを回避できますが、これは私の意見ではこの操作の理想的な動作ではありません。

また、Commitabletransactionオブジェクトを明示的に作成し、アンビエントトランザクションを使用する代わりに、明示的な新しいトランザクションを作成しようとしましたが、それでも運がありません。

これを修正する方法についてのアイデアは、シリアル化可能な接続を使用する呼び出しがreadpastロックヒントを使用しようとするとエラーをスローするため、非常に高く評価されます。

4

3 に答える 3

1

TransactionOptions.IsolationLevelを使用する

デフォルトでは、シリアライズ可能です

TransactionOptions transactionoptions1 = new TransactionOptions();
transactionoptions1.IsolationLevel = IsolationLevel.ReadCommitted;
using (var scope = new TransactionScope(TransactionScopeOption.Required, transactionoptions1))
{
    ... make my 3 stored procedure calls ...

    scope.Complete();

    return returnCode;
}
于 2008-12-04T19:57:18.030 に答える
0

sp_reset_connectionまた、プール内の同じ接続の使用の間にリセット()が表示されるはずです。それは分離レベルをリセットしませんか?シリアル化可能な問題(たとえば、ロックエスカレーションデッドロック)を再現してみましたか?

于 2008-12-04T09:39:46.903 に答える
0

これは、SQLServerでの既知の設計上の決定です。

また、新しいTransactionScope()を使用すると有害と見なされます(2010年6月。デフォルトのコンストラクターは避けてください)

于 2012-07-20T17:06:36.877 に答える