Sql Server 事务嵌套

来源:互联网 发布:淘宝上传图片变形 编辑:程序博客网 时间:2024/05/01 05:33
COMMIT TRANSACTION (Transact-SQL)

 

标志一个成功的隐性事务或显式事务的结束。如果 @@TRANCOUNT 为 1,COMMIT TRANSACTION 使得自从事务开始以来所执行的所有数据修改成为数据库的永久部分,释放事务所占用的资源,并将 @@TRANCOUNT 减少到 0。如果 @@TRANCOUNT 大于 1,则 COMMIT TRANSACTION 使 @@TRANCOUNT 按 1 递减并且事务将保持活动状态。

主题链接图标 Transact-SQL 语法约定

COMMIT { TRAN | TRANSACTION } [ transaction_name | @tran_name_variable ] ][ ; ]

仅当事务被引用所有数据的逻辑都正确时,Transact-SQL 程序员才应发出 COMMIT TRANSACTION 命令。

如果所提交的事务是 Transact-SQL 分布式事务,COMMIT TRANSACTION 将触发 MS DTC 使用两阶段提交协议,以便提交所有涉及该事务的服务器。如果本地事务跨越同一数据库引擎实例上的两个或多个数据库,则该实例将使用内部的两阶段提交来提交所有涉及该事务的数据库。

当在嵌套事务中使用时,内部事务的提交并不释放资源或使其修改成为永久修改。只有在提交了外部事务时,数据修改才具有永久性,而且资源才会被释放。当 @@TRANCOUNT 大于 1 时,每发出一个 COMMIT TRANSACTION 命令只会使 @@TRANCOUNT 按 1 递减。当 @@TRANCOUNT 最终递减为 0 时,将提交整个外部事务。因为 transaction_name 被数据库引擎忽略,所以当存在显著内部事务时,发出一个引用外部事务名称的 COMMIT TRANSACTION 只会使 @@TRANCOUNT 按 1 递减。

当 @@TRANCOUNT 为 0 时发出 COMMIT TRANSACTION 将会导致出现错误;因为没有相应的 BEGIN TRANSACTION。

不能在发出一个 COMMIT TRANSACTION 语句之后回滚事务,因为数据修改已经成为数据库的一个永久部分。

仅当事务计数在语句开始处为 0 时,SQL Server 2000 及更高版本中的数据库引擎才会增加语句内的事务计数。在 SQL Server 7.0 版中,事务计数始终增加,而不考虑在语句开始处为何值。这可能会导致 SQL Server 2000 及更高版本的触发器的 @@TRANCOUNT 中返回的值低于 SQL Server 7.0 版中的对应值。

在 SQL Server 2000 及更高版本中,如果在触发器中执行 COMMIT TRANSACTION 或 COMMIT WORK 语句,并且在触发器的开始位置没有对应的显式或隐式 BEGIN TRANSACTION 语句,则用户看到的行为可能与在 SQL Server 7.0 版中看到的行为有所不同。建议不要在触发器中使用 COMMIT TRANSACTION 或 COMMIT WORK 语句。

要求具有 public 角色成员资格。

A. 提交事务。

此示例将删除候选作业。

复制代码
USE AdventureWorks;GOBEGIN TRANSACTION;GODELETE FROM HumanResources.JobCandidate    WHERE JobCandidateID = 13;GOCOMMIT TRANSACTION;GO

B. 提交嵌套事务。

以下示例创建一个表,生成三个级别的嵌套事务,然后提交该嵌套事务。尽管每个 COMMIT TRANSACTION 语句都有一个 transaction_name 参数,但是 COMMIT TRANSACTION 和 BEGIN TRANSACTION 语句之间没有任何关系。transaction_name 参数仅是帮助阅读的方法,可帮助程序员确保提交的正确号码被编码以便将 @@TRANCOUNT 减少到 0,从而提交外部事务。

复制代码
USE AdventureWorks;GOIF OBJECT_ID(N'TestTran',N'U') IS NOT NULL    DROP TABLE TestTran;GOCREATE TABLE TestTran (Cola INT PRIMARY KEY, Colb CHAR(3));GO-- This statement sets @@TRANCOUNT to 1.BEGIN TRANSACTION OuterTran;GOPRINT N'Transaction count after BEGIN OuterTran = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GOINSERT INTO TestTran VALUES (1, 'aaa');GO-- This statement sets @@TRANCOUNT to 2.BEGIN TRANSACTION Inner1;GOPRINT N'Transaction count after BEGIN Inner1 = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GOINSERT INTO TestTran VALUES (2, 'bbb');GO-- This statement sets @@TRANCOUNT to 3.BEGIN TRANSACTION Inner2;GOPRINT N'Transaction count after BEGIN Inner2 = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GOINSERT INTO TestTran VALUES (3, 'ccc');GO-- This statement decrements @@TRANCOUNT to 2.-- Nothing is committed.COMMIT TRANSACTION Inner2;GOPRINT N'Transaction count after COMMIT Inner2 = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GO-- This statement decrements @@TRANCOUNT to 1.-- Nothing is committed.COMMIT TRANSACTION Inner1;GOPRINT N'Transaction count after COMMIT Inner1 = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GO-- This statement decrements @@TRANCOUNT to 0 and-- commits outer transaction OuterTran.COMMIT TRANSACTION OuterTran;GOPRINT N'Transaction count after COMMIT OuterTran = '    + CAST(@@TRANCOUNT AS NVARCHAR(10));GO
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 穿越兽世:种田驭夫乐悠悠 不灭战神 我在宝可梦世界开餐厅 爸爸,我是来当你同学的 这个主角明明很强却异常谨慎 四合院:我的穿越为啥这么陋 甩了线上男友后我被亲哭了 人在南天坐看万古 为了成为英灵我只好在历史里搞事 我成了游戏里的反派之王 离婚后,前夫每天都想上位 霍格沃茨的风与鹰翼 攻略暴君后,我抱错大腿了 我的精灵模拟器 金鸾喜嫁 人在美漫,开局枪斗术 大国科技从手机开始 人住超神,渣在诸天 斗罗之王者吕布降临 从白蛇开始诸天改命 诸天之天外降临者 屠龙之前就读过龙族的路明非 足球盛宴,从收购欧洲俱乐部开始 在漫威驱魔的魔鬼神父 柯南之我的老姐毛利兰 重生在电影的世界 美漫第一仙 签到从遮天开始 风云饲养师 穿越异世:开局拥有空间神器 吞噬星空之超脱之路 穿梭两界:我携带的物品能变强 从开端开始的超凡之旅 相亲后,靳先生突然黏上我 港综世界的炼金术师 惊!帝君娇宠的小废柴竟然有空间 海上升明帝 开局十连抽,超跑豪宅拿来吧你! 柯学世界的普通警察 柯学世界里的柯研人 我只是个平平无奇的道士啊