0

を実行するメソッドを作成しようとしていますTransaction
私はコードの 2 つのバージョンを思いつきました。
私のテストの 1 つで、例外に直面した後SqlServer2012、トランザクション中にいくつかの行がテーブルに挿入されていることに気付きました。
だから私はそれがトランザクション自体に問題があるに違いないと考え、その問題に対処するためにそれを変更しました.
このメソッドを4回の挿入、1回の削除、1回の更新、および別の挿入コマンドで実行することで得られる例外は次のとおりです。

トランザクション (プロセス ID 59) は、別のプロセスとのロック リソースでデッドロックされ、デッドロックの犠牲者として選択されました。トランザクションを再実行してください。

テーブルを見ると、3 つの新しい挿入行が表示されます (更新に到達してから例外が発生します) !!

更新 両方のメソッドが同じ例外をスローするようになりました。2番目の方法では、新しいパラメーターを追加して古い値をクリアするのにも苦労しました。

最初のバージョンは次のとおりです。

public static int ExecuteTransaction(List<SqlCommand> Commands, IsolationLevel isolationLevel)
{
    int record = -1;
    using (SqlConnection con = new SqlConnection(connectionString))
    {
        con.Open();
        SqlTransaction tr = con.BeginTransaction(isolationLevel);
        try
        {
            foreach (SqlCommand cmd in Commands)
            {
                cmd.Connection = con;
                cmd.Transaction = tr;
                record = cmd.ExecuteNonQuery();
                cmd.Dispose();
            }

            tr.Commit();
        }
        catch (Exception ex)
        {
            tr.Rollback();
            throw ex;
        }
    }

    return record;
}

これは 2 番目のバージョンです。

public static int ExecuteTransaction(List<SqlCommand> Commands, IsolationLevel isolationLevel)
{
    int record = -1;
    using (SqlConnection con = new SqlConnection(connectionString))
    {
        con.Open();
        SqlTransaction tr = con.BeginTransaction(isolationLevel);
        try
        {
            using (SqlCommand cmd = new SqlCommand())
            {
                cmd.Connection = con;
                cmd.Transaction = tr;
                foreach (SqlCommand sqlcmd in Commands)
                {
                    cmd.CommandText = sqlcmd.CommandText;
                    cmd.Parameters.Clear();
                    foreach (SqlParameter param in sqlcmd.Parameters)
                    {
                        cmd.Parameters.AddWithValue(param.ParameterName, param.Value);
                    }
                    record = cmd.ExecuteNonQuery();
                    sqlcmd.Dispose();
                }
            }


            tr.Commit();
        }
        catch (Exception ex)
        {
            tr.Rollback();
            throw ex;
        }
    }

    return record;
}
4

0 に答える 0