SQLServer之创建显式事务
顯式事務(wù)定義
顯式事務(wù)以 BEGIN TRANSACTION 語句開始,并以 COMMIT 或 ROLLBACK 語句結(jié)束。
備注
BEGIN TRANSACTION 使 @@TRANCOUNT 按 1 遞增。
BEGIN TRANSACTION 代表一點,由連接引用的數(shù)據(jù)在該點邏輯和物理上都一致的。?如果遇上錯誤,在 BEGIN TRANSACTION 之后的所有數(shù)據(jù)改動都能進(jìn)行回滾,以將數(shù)據(jù)返回到已知的一致狀態(tài)。?每個事務(wù)繼續(xù)執(zhí)行直到它無誤地完成并且用 COMMIT TRANSACTION 對數(shù)據(jù)庫作永久的改動,或者遇上錯誤并且用 ROLLBACK TRANSACTION 語句擦除所有改動。
BEGIN TRANSACTION 為發(fā)出本語句的連接啟動一個本地事務(wù)。?根據(jù)當(dāng)前事務(wù)隔離級別的設(shè)置,為支持該連接所發(fā)出的?Transact-SQL?語句而獲取的許多資源被該事務(wù)鎖定,直到使用 COMMIT TRANSACTION 或 ROLLBACK TRANSACTION 語句完成該事務(wù)為止。?長時間處于未完成狀態(tài)的事務(wù)會阻止其他用戶訪問這些鎖定的資源,也會阻止日志截斷。
雖然 BEGIN TRANSACTION 啟動一個本地事務(wù),但是在應(yīng)用程序接下來執(zhí)行一個必須記錄的操作(如執(zhí)行 INSERT、UPDATE 或 DELETE 語句)之前,它并不被記錄在事務(wù)日志中。?應(yīng)用程序能執(zhí)行一些操作,例如為了保護(hù) SELECT 語句的事務(wù)隔離級別而獲取鎖,但是直到應(yīng)用程序執(zhí)行一個修改操作后日志中才有記錄。
在一系列嵌套的事務(wù)中用一個事務(wù)名給多個事務(wù)命名對該事務(wù)沒有什么影響。?系統(tǒng)僅登記第一個(最外部的)事務(wù)名。?回滾到其他任何名稱(有效的保存點名除外)都會產(chǎn)生錯誤。?事實上,回滾之前執(zhí)行的任何語句都不會在錯誤發(fā)生時回滾。?這些語句僅當(dāng)外層的事務(wù)回滾時才會進(jìn)行回滾。
如果在語句提交或回滾之前執(zhí)行了如下操作,由 BEGIN TRANSACTION 語句啟動的本地事務(wù)將升級為分布式事務(wù):
-
執(zhí)行一個引用鏈接服務(wù)器上的遠(yuǎn)程表的 INSERT、DELETE 或 UPDATE 語句。?如果用于訪問鏈接服務(wù)器的 OLE DB 訪問接口不支持 ITransactionJoin 接口,則 INSERT、UPDATE 或 DELETE 語句會失敗。
-
當(dāng)啟用了 REMOTE_PROC_TRANSACTIONS 選項時,將調(diào)用遠(yuǎn)程存儲過程。
SQL Server?的本地副本成為事務(wù)控制器并且使用?Microsoft?分布式事務(wù)處理協(xié)調(diào)器 (MS DTC) 來管理分布式事務(wù)。
使用 BEGIN DISTRIBUTED TRANSACTION 可以將事務(wù)作為分布式事務(wù)顯式執(zhí)行。?有關(guān)詳細(xì)信息,請參閱?BEGIN DISTRIBUTED TRANSACTION (Transact-SQL)。
SET IMPLICIT_TRANSACTIONS 設(shè)置為 ON 時,BEGIN TRANSACTION 語句創(chuàng)建兩個嵌套的事務(wù)。?有關(guān)詳細(xì)信息,請參閱?SET IMPLICIT_TRANSACTIONS (Transact-SQL)
標(biāo)記的事務(wù)
WITH MARK 選項使事務(wù)名被置于事務(wù)日志中。?將數(shù)據(jù)庫還原到早期狀態(tài)時,可使用標(biāo)記事務(wù)代替日期和時間。?有關(guān)詳細(xì)信息,請參閱?使用標(biāo)記的事務(wù)一致地恢復(fù)相關(guān)的數(shù)據(jù)庫的事務(wù)(完全恢復(fù)模式)和?RESTORE (Transact-SQL)。
另外,若要將一組相關(guān)數(shù)據(jù)庫恢復(fù)到邏輯上一致的狀態(tài),必須使用事務(wù)日志標(biāo)記。?標(biāo)記可由分布式事務(wù)置于相關(guān)數(shù)據(jù)庫的事務(wù)日志中。?將這組相關(guān)數(shù)據(jù)庫恢復(fù)到這些標(biāo)記將產(chǎn)生一組在事務(wù)上一致的數(shù)據(jù)庫。?在相關(guān)數(shù)據(jù)庫中放置標(biāo)記需要特殊的過程。
只有當(dāng)數(shù)據(jù)庫由標(biāo)記事務(wù)更新時,才在事務(wù)日志中放置標(biāo)記。?不修改數(shù)據(jù)的事務(wù)不被標(biāo)記。
使用T-SQL腳本創(chuàng)建顯式事務(wù)
語法:
--聲明數(shù)據(jù)庫引用
use 數(shù)據(jù)庫名稱;
go
begin?{ tran| transaction }?[ { transaction_name | @tran_name_variable }?[ with mark [ 'description' ] ]
begin
業(yè)務(wù)代碼1;
save? { tran | transaction } { savepoint_name | @savepoint_variable };
rollback?{ tran | transaction } [ transaction_name | @tran_name_variable | savepoint_name | @savepoint_variable ];
commit { tran | transaction }??{ transaction_name | @tran_name_variable } with(delayed_durability=on);
end
go
語法解析:
--begin transaction transaction_name
--適用范圍:SQL Server(從 2008 版開始)和 Azure SQL Database
--分配給事務(wù)的名稱。 transaction_name 必須符合標(biāo)識符規(guī)則,但標(biāo)識符所包含的字符數(shù)不能大于 32。 僅在最外面的 BEGIN...COMMIT 或 BEGIN...ROLLBACK 嵌套語句對中使用事務(wù)名。
--transaction_name 始終區(qū)分大小寫,即使 SQL Server 實例不區(qū)分大小寫也是如此。
--begin transaction @tran_name_variable?
--適用范圍:SQL Server(從 2008 版開始)和 Azure SQL Database
--用戶定義的、含有有效事務(wù)名稱的變量的名稱。 必須使用 char、varchar、nchar 或 nvarchar 數(shù)據(jù)類型聲明該變量。 如果傳遞給該變量的字符多于 32 個,則僅使用前面的 32 個字符;其余的字符將被截斷。
--with mark [ 'description' ]
--適用范圍:SQL Server(從 2008 版開始)和 Azure SQL Database
--指定在日志中標(biāo)記事務(wù)。 description 是描述該標(biāo)記的字符串。 在將長于 128 個字符的 description 存儲到 msdb.dbo.logmarkhistory 表中之前,先將其截斷為 128 個字符。
--如果使用了 WITH MARK,則必須指定事務(wù)名。 WITH MARK 允許將事務(wù)日志還原到命名標(biāo)記。
--save transaction savepoint_name
--分配給保存點的名稱。 保存點名稱必須符合標(biāo)識符的規(guī)則,但長度不能超過 32 個字符。 savepoint_name 始終區(qū)分大小寫,即使 SQL Server 實例不區(qū)分大小寫也是如此。
--save transaction @savepoint_variable?
--包含有效保存點名稱的用戶定義變量的名稱。 必須使用 char、varchar、nchar 或 nvarchar 數(shù)據(jù)類型聲明該變量。 如果長度超過 32 個字符,也可以傳遞到變量,但只使用前 32 個字符。
--rollback { tran | transaction } [ transaction_name | @tran_name_variable | savepoint_name | @savepoint_variable ];
--將顯式事務(wù)或隱性事務(wù)回滾到事務(wù)的起點或事務(wù)內(nèi)的某個保存點。 可以使用 ROLLBACK TRANSACTION 清除自事務(wù)的起點或到某個保存點所做的所有數(shù)據(jù)修改。 它還釋放由事務(wù)控制的資源。
--commit { tran | transaction } { transaction_name | @tran_name_variable };
--標(biāo)志一個成功的隱性事務(wù)或顯式事務(wù)的結(jié)束。 如果 @@TRANCOUNT 為 1,COMMIT TRANSACTION 使得自從事務(wù)開始以來所執(zhí)行的所有數(shù)據(jù)修改成為數(shù)據(jù)庫的永久部分,釋放事務(wù)所占用的資源,并將 @@TRANCOUNT 減少到 0。
--如果 @@TRANCOUNT 大于 1,則 COMMIT TRANSACTION 使 @@TRANCOUNT 按 1 遞減并且事務(wù)將保持活動狀態(tài)。
--delayed_durability
--適用范圍:SQL Server 和 Azure SQL 數(shù)據(jù)庫
--請求將此事務(wù)與延遲持續(xù)性一起提交的選項。 如果已用 DELAYED_DURABILITY = DISABLED 或 DELAYED_DURABILITY = FORCED 更改了數(shù)據(jù)庫,則忽略該請求。 有關(guān)詳細(xì)信息,請參閱主題控制事務(wù)持續(xù)性。
示例:
--聲明數(shù)據(jù)庫引用
use testss;
go
begin transaction explicittran
with mark '開啟一個顯式事務(wù)'
begin
declare @counts int =0;
insert into test1(name,sex,age,classid,height) values('事務(wù)測試','男','21','20','178');
set @counts=@counts+(select @@ROWCOUNT);
save tran inserttran1;--回滾點一,事務(wù)已經(jīng)插入了一條數(shù)據(jù)
insert into test2(name) values('事務(wù)測試');
set @counts=@counts+(select @@ROWCOUNT);
save tran inserttran2;--回滾點二,事務(wù)已經(jīng)插入了二條數(shù)據(jù)
insert into test3(name,sex,age,classid) values('事務(wù)班','男','asd','23');
set @counts=@counts+(select @@ROWCOUNT);
save tran inserttran3;--回滾點三,事務(wù)已經(jīng)插入了三條數(shù)據(jù)
--出錯回滾到回滾點
if @counts=3
rollback transaction inserttran3;
else if @counts=2
rollback transaction inserttran2;
else if @counts=1
rollback transaction inserttran1;
--提交事務(wù)或者回滾事務(wù)
if @counts<>0
commit transaction explicittran
--with(delayed_durability=on)
;
else
rollback transaction explicittran;
end
go
示例結(jié)果:
?
轉(zhuǎn)載于:https://www.cnblogs.com/vuenote/p/9923626.html
總結(jié)
以上是生活随笔為你收集整理的SQLServer之创建显式事务的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: RESTful API接口文档规范小坑
- 下一篇: 小米oj 有多少个公差为2的等差数列