32

ADO.NET SqlCommand オブジェクトを作成し、データベース (SQL Server 2005) に保存されるアイテムのリストをループする小さな C# メソッドを "継承" しました。

現在、従来の SqlConnection/SqlCommand アプローチが使用されており、すべてが機能することを確認するために、2 つの手順 (古いエントリを削除してから新しいエントリを挿入する) が ADO​​.NET SqlTransaction にラップされています。

using (SqlConnection _con = new SqlConnection(_connectionString))
{
   using (SqlTransaction _tran = _con.BeginTransaction())
   {
      try
      {
         SqlCommand _deleteOld = new SqlCommand(......., _con);
         _deleteOld.Transaction = _tran;
         _deleteOld.Parameters.AddWithValue("@ID", 5);

         _con.Open();

         _deleteOld.ExecuteNonQuery();

         SqlCommand _insertCmd = new SqlCommand(......, _con);
         _insertCmd.Transaction = _tran;

         // add parameters to _insertCmd

         foreach (Item item in listOfItem)
         {
            _insertCmd.ExecuteNonQuery();
         }

         _tran.Commit();
         _con.Close();
       }
       catch (Exception ex)
       {
          // log exception
          _tran.Rollback();
          throw;
       }
    }
}

さて、私は最近 .NET TransactionScope クラスについて多くのことを読んでいて、ここでどのようなアプローチが望ましいのか疑問に思っていました。使用に切り替えることで何か(読みやすさ、速度、信頼性)が得られますか

using (TransactionScope _scope = new TransactionScope())
{
  using (SqlConnection _con = new SqlConnection(_connectionString))
  {
    ....
  }

  _scope.Complete();
}

あなたは何を好みますか、そしてその理由は何ですか?

マルク

4

6 に答える 6

19

を使用するように既存のコードを切り替えても、すぐには何も得られませんTransactionScope。柔軟性があるため、将来の開発に使用する必要があります。将来的には、ADO.NET呼び出し以外のものをトランザクションに含めることが容易になります。

ところで、投稿された例では、SqlCommandインスタンスはusingブロック内にある必要があります。

于 2009-08-13T17:08:05.737 に答える
10

私はTransactionScopeを好みます。すべてのシナリオで完全に機能するわけではありませんが、あなたが説明したシナリオでは、より良い解決策です.

私の推論:

  1. トランザクションへの登録は自動です
  2. 例外が発生した場合のトランザクションのロールバックは自動です

全体として、システムが詳細の一部を処理しているため、結果としてコードが少し少なくなり、全体的により堅牢な設計になります。覚えておかなければならないことが 1 つ減ります。

さらに、透過的なトランザクション登録は、DAL に多数のネストされたメソッドがある場合に特に役立ちます。同じ DB を指している場合でも、複数の SqlConnections を使用します。

于 2009-11-18T07:45:16.030 に答える
8

Microsoft は、トランザクション スコープを使用することをお勧めします。

http://msdn.microsoft.com/en-us/library/system.transactions.transactionscope.aspx

基本的な考え方は、トランザクション スコープが「周囲のトランザクション コンテキスト」を管理するというものです。1 つのデータベースと対話することから始めます。SQL トランザクションがあり、次にデータベース番号 2 と対話すると、トランザクションは分散トランザクションに昇格します。

トランザクション スコープは機能するため、配管ではなくシステムの機能に集中できます。

編集

トランザクション スコープを使用すると、そのスコープ内のすべてがトランザクションによってカバーされます。したがって、コマンドをトランザクションに接続するコード行を保存します。これはエラーの原因となる可能性があります。たとえば、この行が忘れられている可能性が 1000 分の 1 である場合、何行が欠落しているでしょうか。

編集2

以下の Triynko に関するコメントに同意します。ただし、Entity Framework を使用すると、EF は自動的に接続を閉じて再度開き、トランザクションに参加させます。接続を物理的に閉じるのではなく、接続プールに解放し、同じものでも別のものでもよい新しいものを取得します。

于 2009-08-13T13:08:40.700 に答える
7

DTC、ファイアウォールなどの設定など、サーバーで実行する必要のある多くの設定のため、トランザクションスコープを使用すると、多くの問題が発生する場合があることに注意してください。したがって、実装ではSqlTransactionを使用する方が節約できます。

于 2009-11-18T00:55:07.687 に答える
2

わかりました、これには遅すぎるかもしれません...しかし、とにかく、興味のある人のために書き留めておきます...

SqlTransaction現在のベースのアプローチで多くの困難を経験した後、今ではより良いイメージを持っているので、私がTransactionScope見ているTransactionScopeように、 .

于 2011-06-09T22:03:55.927 に答える