在一个SP中执行BEGIN TRANS-COMMIT TRANS并在TransactionScope中执行多个SP并在完成范围之前引发错误时会发生什么。

所以伪代码如下

//Using TransactionScope() {
//   executing SP1
//   executing SP2
//   executing SP3
//   throw new Exception();
//}


SP2包含以下代码。

// BEGIN TRANS
//   Update Statement1
//   Update Statement2
//   Update Statement3
// COMMIT TRANS


如果我们假设事务在SP2中提交,将会发生什么?


一切都回滚
SP2中的3条语句被提交。其他一切都回滚了吗?


我不知道这是否重要,但以防万一,所有三个SP都使用一个连接对象执行,并且该连接在两个ExecuteNonQuery语句之间被关闭并再次打开。

最佳答案

始终只有一个事务,最外部事务由最外部事务作用域启动。在最外面的事务范围内发生的所有其他内部事务范围和所有其他T-SQL代码中的BEGIN事务都不过是@@TRANCOUNT的美化增量,而所有这些COMMITS都是相同的减量。只是最后一次COMMIT才重要,直到那时事务才提交。

因此,在您的示例中,SP2没有提交任何内容。它所做的全部工作将@@ TRANCOUNT递增到2,然后递减回到1。事务仍然处于活动状态,并且当C#代码引发时,事务将回滚。

另外,请参见Exception handling and nested transactions,以获取有关如何编写良好的异常安全存储过程的模板。

10-08 19:47