【问题标题】:Will a DB procedure in a transaction still be rolled back from inside an ADO.net transaction?事务中的 DB 过程是否仍会从 ADO.net 事务内部回滚?
【发布时间】:2012-07-18 16:59:46
【问题描述】:

抱歉,这个问题很难说:

假设我有一个执行一些插入操作的存储过程。它被包装在一个事务中并提交,前提是每个事务都在该事务中顺利进行。

现在,我从 .net 函数中调用该事务。在这个函数中,我必须调用一些其他函数,这些函数也调用以类似方式构建的存储过程。示例:

bool SaveTicket()
{
   using(MyTransaction)
   {
      try
      {
         SaveTicketInfo(); //calls sproc 1
         SaveComments(); //calls sproc 2
         SaveAttachments(); //calls sproc 3
      }
      catch(Exception)
      {
         MyTransactionRollback(); //i would normally wrap this in its own try/catch
      }
   }
}

好的,这就是流程的框架。我在代码中实际做的是检查三个进程中每一个的返回值,如果它们返回 false,我会抛出一个触发回滚的异常。

我想知道的是,如果这些存储过程中有 commits,我的 .net 函数中的回滚是否仍然有效?还是完全没用?

【问题讨论】:

标签: .net database tsql c#-4.0 transactions


【解决方案1】:

是的,它将被回滚。

SQL Server 中的事务可以嵌套。 SQL Server 基本上忽略了内部事务,关闭内部事务的唯一方法是提交它(即提交外部事务,必须提交所有内部事务)。回滚语句只适用于最外层的事务。

您可以在此处阅读更多信息:http://msdn.microsoft.com/en-us/library/ms189336(v=sql.105).aspx

【讨论】:

  • 换句话说,不是吗?重点是能够运行多个存储过程,但如果在所有存储过程都成功完成之前出现问题,则将它们全部回滚。
  • Sinaesthetic,我为我迟钝的原始答案道歉。为了清楚起见,我编辑了我的答案。
【解决方案2】:

我想我首先会问您是否真的需要在存储过程中拥有单独的事务 - 将它们放在那里确实会使维护应用程序代码变得更加困难,并将应用程序逻辑放入持久存储中。

我的直觉是,由于存储过程创建并提交自己的事务,所以当 MyTransaction 回滚时,这些事务不会回滚,但真正的答案可能取决于 DTC 的配置方式。

详情请见this answer

【讨论】:

  • 这不是需要它们的问题。问题是他们已经在那里并且很有机会说服我的 dba 让我处理交易
  • 哈哈,说服 dba 将控制权交给开发人员是一项绝对的挑战!
猜你喜欢
  • 1970-01-01
  • 2014-07-17
  • 2020-04-15
  • 1970-01-01
  • 1970-01-01
  • 2021-10-15
  • 1970-01-01
  • 2015-05-17
  • 1970-01-01
相关资源
最近更新 更多