1. 我有SQL Server 2000,它不支持MultipleActiveResults
  2. 我必须进行多次插入,并且每次插入都需要一个连接。
  3. 我想在所有插入之前开始一个事务,并在所有插入之后完成它。
  4. 我该怎么做?
有帮助吗?

解决方案

您不使用一个连接和多个命令(实际上是在循环中重新创建一个命令)的原因是什么? 也许这个解决方案适合你:

   public static void CommandExecNonQuery(SqlCommand cmd, 
       string query, SqlParameter[] prms)
    {
        cmd.CommandText = query;
        cmd.Parameters.AddRange(prms);
        cmd.ExecuteNonQuery();
        cmd.Parameters.Clear();
    }

    static void Main(string[] args)
    {
        string insertQuery = 
           @"INSERT TESTTABLE (COLUMN1, COLUMN2) " + 
             "VALUES(@ParamCol1, @ParamCol2)";
        using (SqlConnection connection = 
          new SqlConnection(connectionString))
        {
            using (SqlCommand command = 
              connection.CreateCommand())
            {
                SqlTransaction transaction = null;
                try
                {
                    // BeginTransaction() Requires Open Connection
                    connection.Open();

                    transaction = connection.BeginTransaction();

                    // Assign Transaction to Command
                    command.Transaction = transaction;
                    for (int i = 0; i < 100; i++)
                        CommandExecNonQuery(command, insertQuery, 
                          new SqlParameter[] { 
                            new SqlParameter("@ParamCol1", i), 
                            new SqlParameter("@ParamCol2", i.ToString()) });
                    transaction.Commit();
                }
                catch
                {
                    transaction.Rollback();
                    throw;
                }
                finally
                {
                    connection.Close();
                }
            }
        }
    }

另见
Sql Server Transactions - ADO.NET 2.0 - 提交和回滚 - 使用声明 - IDisposable

其他提示

您没有指定是否使用.NET 2.0,但我会做出这样的假设。 C#3.0示例代码如下:

using (var tx = new TransactionScope()) {
    // Execute multiple DB statements inside here
    ts.Complete();
}

如果任何DB语句失败,将永远不会到达ts.complete,并且该事务将在using语句结束时自动回滚。但是,这种方法的一个警告是,如果使用多个连接,最终会利用DTC,这意味着性能会降低。

已编辑以将SqlTransaction更改为TransactionScope

强制单个SQL连接以避免使用DTC的示例:

using (var tx = new TransactionScope())
using (var db = new SqlConnection(connString)) {
    // Command 1
    using (var cmd = db.CreateCommand()) {
        cmd.CommandText = "select...";
        using (var reader = cmd.ExecuteReader()) {
           // Process results or store them somewhere for later
        }
    }

    // Command 2
    using (var cmd = db.CreateCommand()) {
        cmd.CommandText = "select...";
        using (var reader = cmd.ExecuteReader()) {
           // Process results or store them somewhere for later
        }
    }

    // Command 3
    using (var cmd = db.CreateCommand()) {
        cmd.CommandText = "select...";
        using (var reader = cmd.ExecuteReader()) {
           // Process results or store them somewhere for later
        }
    }
    tx.Complete();
}

在连接上创建事务,除了创建连接之外没有任何范围,因此您无法按照要求执行操作。重构,以便您可以在连接上顺序执行插入而不是同时执行或实现不同的机制来实现回滚(例如,如果稍后遇到错误,可以用作查找删除插入记录的插入键表。处理)

我认为交易不能跨越多个连接。

在单独的连接中进行多次插入的原因是什么?我认为你通常会在一个连接中想要它们。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top