提交事务是在动态SQL中启动的?

时间:2017-09-08 15:18:40

标签: sql-server transactions

以下代码按预期运行。插入行。

UWP

然而,它出现以下错误?

  

Msg 266,Level 16,State 2,Line 31

     

EXECUTE之后的事务计数表示BEGIN和COMMIT语句的数量不匹配。先前的计数= 0,当前计数= 1。

更新 我发现如果将代码放在try / catch块中,动态SQL中的create table #t1(a datetime2) declare @s nvarchar(max) = N' -- Some expensive remote query should not be in the transaction begin tran insert #t1 select getdate()'; exec (@s); commit; -- replace commit to rollback will rollback the transaction select * from #t1 语句将不会运行。但是,它仍然有错误。

insert

1 个答案:

答案 0 :(得分:0)

  然而,引擎发出了关于@@ TRANCOUNT不匹配的错误   EXEC之后立即。此外,这个错误毁灭了   交易,不管XACT_ABORT

这里的第二个陈述不正确,正如第一个OP的例子所示,在动态代码中启动的事务可以在外部范围内成功提交。所以交易没有注定,它是可以承诺的。

我没有在OP中找到问题。如果它是关于如何处理266错误,那么答案就是忽略它。

266错误消息仅供参考,您可以在此处查看: Rollbacks and Commits in Stored Procedures and Triggers

  

如果存储过程完成,则@@ TRANCOUNT具有不同的值   比执行程序时的信息错误   (266)发生

所以这里发生的是服务器在执行存储过程/动态sql时保存@@TRANCOUNT,当你返回到外部作用域时,它控制@@TRANCOUNT是否与启动sp /时相同动态代码,如果不是这种情况,它会引发266错误,即“根本不会终止任何错误”,并且仅被视为信息性。