【问题标题】:How to implement Transaction?如何实现交易?
【发布时间】:2013-03-07 19:28:50
【问题描述】:

我正在研究 sql,我的查询是我有一些方法可以在其中执行不同的任务。例如:- 第一种方法 - 插入 第二种方法 - 更新 第三种方法 - 删除 第四种方法 - 插入

现在我想一次性执行所有这些。但如果发生任何错误,则整个过程会自行回滚。

代码:

private void btnSubmit_Click(object sender, EventArgs e)
{
    DialogResult dr = MessageBox.Show("Are you sure you want to submit the information? Click 'Yes' to Submit or 'No' to re-Check.", "eParty - Confirmation", MessageBoxButtons.YesNo, MessageBoxIcon.Information);
    if (dr == DialogResult.Yes)
    {
        this.Cursor = Cursors.WaitCursor;

        INSERT();
        UPDATE();
        DELETE();
        INSERTAGAIN();

        MessageBox.Show("Booked successfully.", "eParty - Done!", MessageBoxButtons.OK, MessageBoxIcon.Information);
        this.Cursor = Cursors.Default;

        this.Cursor = Cursors.WaitCursor;

        this.Close();
    }
    else
    {

    }
}

现在如何在 'btnSubmit_Click' 方法中实现事务...

【问题讨论】:

    标签: c# sql


    【解决方案1】:

    试试这个:

      using(var scope = new TransactionScope())
      {
        INSERT();
        UPDATE();
        DELETE();
        INSERTAGAIN();
    
        scope.Complete(); //if we make it here - commit the changes, 
                          //if not - everything is rolled back
    
      }
    

    记得在你的项目中加入System.Transactions

    【讨论】:

      【解决方案2】:

      这取决于你有什么数据库访问技术。

      如果您使用实体框架,SaveChanges() 方法已经支持事务。

      如果是纯 ADO.NET,请参阅https://stackoverflow.com/a/224702/210994

      【讨论】:

        【解决方案3】:

        您可以使用 ADO 事务并将您的事务作为参数发送到您的所有方法

        SqlConnection db = new SqlConnection("connstringhere");
        SqlTransaction transaction;
        db.Open();
        transaction = db.BeginTransaction();
        try 
        {
             INSERT(transaction);
             UPDATE(transaction);
             DELETE(transaction);
             INSERT(transaction);
             transaction.Commit();
        } 
        catch (SqlException sqlError) 
        {
             transaction.Rollback();
        }
        

        【讨论】:

        • 先生,我实现了您的代码,但我不知道如何使我的方法可返回。您能否告诉我应该对我的所有方法进行哪些更改。我正在使用这个:public void INSERT() { //代码 }
        • @SandeepKumarThenua 你好。您可以使用 SqlCommand.ExecuteNonQuery 来返回由您的查询生成的受影响行数。所以如果是-1,则抛出SqlExecption。另一种方法是为您的服务器捕获@@error,并在您的代码中处理它。或者您可以在您的方法中返回受影响的行数: public long INSERT() { //the code;返回 SqlCommand.ExecuteNonQuery(); },如果为-1则回滚
        【解决方案4】:

        通常是这样的:

        void DoStuff(args)
        {
            using (var conn = CreateOpenConnection())
            using (var tran = conn.BeginTransaction())
            {
                try
                {
                    // various operations here
                    ForExample(conn, tran);
                    tran.Commit();
                }
                catch
                {
                    tran.Rollback();
                    throw;
                }
            }
        }
        
        void ForExample(DbConnection conn, DbTransaction tran = null)
        {
            using (var cmd = conn.CreateCommand())
            {
                cmd.Transaction = tran;
                cmd.CommandText = "For example";
                // cmd.Parameters.Add(...)
                cmd.ExecuteNonQuery();
            }
        }
        

        尽管可以使用位于原始 ADO.NET 之上的任何可用工具/库来减少大部分问题。

        【讨论】:

          【解决方案5】:

          您可以使用 .Net 的 TransactionScope 类来实现这一点。 http://msdn.microsoft.com/en-us/library/system.transactions.transactionscope.aspx 您可以根据需要选择隔离级别。如果您不确定,请使用最一致且性能最低的 Serializable 级别。但是,如果您的 sql 存储过程具有隔离级别,它们将获得优先权。如果这是一个关键设计,请在继续之前阅读事务。

          【讨论】:

            【解决方案6】:

            也许您应该创建一个存储过程并根据参数执行您的 CRUD 操作。例如:

                BEGIN TRANSACTION
            
                IF(@PartyID <= 0)
                BEGIN
                    //INSERT
                IF @@ERROR <> 0
                    BEGIN
                        ROLLBACK TRANSACTION
                        RETURN
                    END
                END
                ELSE
                BEGIN
                    //UPDATE
                IF @@ERROR <> 0
                    BEGIN
                        ROLLBACK TRANSACTION
                        RETURN
                    END
                END
            

            【讨论】:

              【解决方案7】:

              请参考本主题:Implementing an Implicit Transaction using Transaction Scope

              TransactionScope 类提供了一种简单的方法来标记一个块 代码作为参与交易,而无需您 与交易本身进行交互。事务范围可以选择 并自动管理环境事务。由于其易于 使用和效率,建议您使用 开发事务应用程序时的 TransactionScope 类。在 此外,您无需使用 交易。任何 System.Transactions 资源管理器(例如 SQL Server 2005) 可以检测环境事务的存在 由作用域创建并自动登记。

              我还想建议您阅读此question 及其答案。它涉及有关在多个连接上使用事务的有趣主题。

              【讨论】:

                猜你喜欢
                • 2018-07-23
                • 1970-01-01
                • 2013-08-29
                • 2021-08-14
                • 2018-11-20
                • 2020-10-24
                • 1970-01-01
                • 1970-01-01
                • 1970-01-01
                相关资源
                最近更新 更多