7.1 認(rèn)識事務(wù)
7.1.1 概述
事務(wù)可由一條非常簡單的SQL語句組成垫桂,也可以由一組復(fù)雜的SQL語句組成猜惋。事務(wù)是訪問并更新數(shù)據(jù)庫中各種數(shù)據(jù)項(xiàng)的一個程序執(zhí)行單元折汞。在事務(wù)中的操作咒劲,要么都做修改,要么都不做饲齐,這就是事務(wù)的目的钉凌,也是事務(wù)模型區(qū)別與文件系統(tǒng)的重要區(qū)別之一。理論上說捂人,事務(wù)有著極其嚴(yán)格的定義御雕,它必須同時(shí)滿足四個特性矢沿,即通常所說的事務(wù)的ACID特性。但是數(shù)據(jù)庫廠商處于各種目的酸纲,并沒有嚴(yán)格去滿足事務(wù)的ACID標(biāo)準(zhǔn)捣鲸。對于InnoDB存儲引擎而言,其默認(rèn)的事務(wù)隔離級別為READ REPEATABLE 闽坡,完全遵循和滿足事務(wù)的ACID特性栽惶。
A(Atomicity),原子性疾嗅。原子性是指整個數(shù)據(jù)庫事務(wù)是一個不可分割的工作單位外厂。只有事務(wù)中所有的數(shù)據(jù)庫操作都執(zhí)行成功,才算整個事務(wù)成功代承。事務(wù)中任何一個SQL語句執(zhí)行失敗汁蝶,已經(jīng)執(zhí)行成功的SQL語句也必須撤銷,數(shù)據(jù)庫狀態(tài)應(yīng)該退回到執(zhí)行事務(wù)前的狀態(tài)论悴。
C(Consistency)掖棉,一致性。一致性是指事務(wù)從一種狀態(tài)轉(zhuǎn)變?yōu)橄乱环N一致的狀態(tài)意荤,在事務(wù)開始之前和事務(wù)結(jié)束以后啊片,數(shù)據(jù)庫完整性約束沒有被破壞只锻。例如玖像,在表中有一個字段為姓名,為唯一性約束齐饮。如果有一個事務(wù)對姓名字段進(jìn)行了修改捐寥,但是在事務(wù)提交或事務(wù)發(fā)生回滾之后,表中姓名字段變得非唯一了祖驱,這就破壞了事務(wù)的一致性要求握恳,即事務(wù)將數(shù)據(jù)庫從一種狀態(tài)變成了一種不一致的狀態(tài)。
D(Durability)捺僻,持久性乡洼。事務(wù)一旦提交,其結(jié)果就是永久性的匕坯。即使發(fā)生宕機(jī)等故障束昵,數(shù)據(jù)庫也能將數(shù)據(jù)恢復(fù)。持久性保證事務(wù)系統(tǒng)的高可靠性(High Reliability)葛峻,而不是高可用性(High Availablity)锹雏。
7.1.2 分類
從事務(wù)理論的角度來說,可用把事務(wù)分為以下幾種類型:
- 扁平事務(wù)(Flat Transactions)
- 帶有保存點(diǎn)的扁平事務(wù)(Flat Transactions with Savepoints)
- 鏈?zhǔn)聞?wù)(Chained Transactionss)
- 嵌套事務(wù)(Nested Transactions)
- 分布式事務(wù)(Distributed Transactions)
扁平事務(wù)(Flat Transaction)
事務(wù)類型中最簡單也是使用最為頻繁的事務(wù)术奖。在扁平事務(wù)中礁遵,所有操作都處于同一層次轻绞,其有BEGIN WORK開始,有COMMIT WORK或ROLLBACK WORK結(jié)束佣耐,其間的操作都是原子的政勃,要么都執(zhí)行,要么都回滾晰赞。扁平事務(wù)的主要限制是不能提交或者回滾事務(wù)的某一部分稼病,或分幾個步驟提交。如果要支持有計(jì)劃的回滾操作掖鱼,那么就不需要終止整個事務(wù)然走。因此就出現(xiàn)了帶有保存點(diǎn)的扁平事務(wù)
帶有保存點(diǎn)的扁平事務(wù)
除了支持扁平事務(wù)外,允許事務(wù)在執(zhí)行過程中回滾到同一個事務(wù)中較早的一個狀態(tài)戏挡。保存點(diǎn)用來通知系統(tǒng)應(yīng)該記住事務(wù)當(dāng)前的狀態(tài)芍瑞,以便當(dāng)之后發(fā)生錯誤時(shí),事務(wù)能回到保存點(diǎn)當(dāng)時(shí)的狀態(tài)褐墅。保存點(diǎn)用SAVE WORK函數(shù)來建立拆檬,通知系統(tǒng)記錄當(dāng)前的處理狀態(tài)。保存帶你在事務(wù)內(nèi)部是遞增的妥凳,這意味著ROLLBACK WORK不影響保存點(diǎn)的計(jì)數(shù)竟贯,并且單調(diào)遞增的編號能保持事務(wù)執(zhí)行的整個歷史過程,包括在執(zhí)行過程中想法的改變逝钥。
鏈?zhǔn)聞?wù)
可視為保存點(diǎn)模式的一種變種屑那。帶有保存點(diǎn)的扁平事務(wù),當(dāng)系統(tǒng)發(fā)生崩潰是艘款,所有保存點(diǎn)都將消失持际,因?yàn)槠浔4纥c(diǎn)是易失的,而非持久的哗咆。這意味著當(dāng)進(jìn)行恢復(fù)是蜘欲,事務(wù)需要從開始處重新執(zhí)行,而不能從最近的一個保存點(diǎn)繼續(xù)執(zhí)行晌柬。
鏈?zhǔn)聞?wù)的思想是:在提交一個事務(wù)時(shí)姥份,釋放不需要的數(shù)據(jù)對象,將必要的處理上下文隱式地傳給下一個要開始的事務(wù)年碘。注意澈歉,提交事務(wù)操作和開始下一個事務(wù)操作將合并為一個原子操作。這意味著下一個事務(wù)能看到上一個事務(wù)的結(jié)果盛泡,就好像在一個事務(wù)中進(jìn)行一樣闷祥。
鏈?zhǔn)聞?wù)和帶有保存點(diǎn)的扁平事務(wù)不同的是,帶有保存點(diǎn)的扁平事務(wù)能回滾到任意正確的保存點(diǎn)。而鏈?zhǔn)聞?wù)的回滾僅限于當(dāng)前事務(wù)凯砍,即只能恢復(fù)到最近一個保存點(diǎn)箱硕。對于鎖的處理,兩者也不同悟衩。鏈?zhǔn)聞?wù)在執(zhí)行commit之后即釋放了當(dāng)前事務(wù)所持有的鎖剧罩,而帶有保存點(diǎn)的扁平事務(wù)不影響迄今為止所持有的鎖。
嵌套事務(wù)
有一個頂層事務(wù)控制著各個層次的事務(wù)座泳。頂層事務(wù)之下嵌套的事務(wù)被稱為子事務(wù)惠昔,其控制每一個局部的變換。
1.嵌套事務(wù)是由若干事務(wù)組成的一棵樹挑势,子樹既可以是嵌套事務(wù)镇防,也可以是扁平事務(wù)
2.處在葉節(jié)點(diǎn)的事務(wù)是扁平事務(wù)。但是每個子事務(wù)從根到葉節(jié)點(diǎn)的距離可以是不同的潮饱。
3.位于根節(jié)點(diǎn)的事務(wù)稱為頂層事務(wù)来氧,其他事務(wù)稱為子事務(wù)卿捎。事務(wù)的前驅(qū)稱為父事務(wù)挽荠,事務(wù)的下一層稱為兒子事務(wù)。
4.子事務(wù)既可以提交屁柏,也可以回滾凫碌。但是它的提交并不馬上生效扑毡,除非其父事務(wù)已經(jīng)提交。因此可以推出盛险,任何子事務(wù)都在頂層事務(wù)提交之后才能真正的提交瞄摊。
5.樹中的任意一個事務(wù)的回滾會引起它的所有子事務(wù)一同回滾,故子事務(wù)僅保留A枉层,C泉褐,I 特性赐写,不具有D的特性
分布式事務(wù)
通常是在一個分布式環(huán)境下運(yùn)行的扁平事務(wù)鸟蜡,因此需要根據(jù)數(shù)據(jù)所在位置訪問網(wǎng)絡(luò)中的不同節(jié)點(diǎn)。
7.2 事務(wù)的實(shí)現(xiàn)
事務(wù)的隔離性由鎖來實(shí)現(xiàn)挺邀。原子性揉忘、一致性、持久性通過數(shù)據(jù)庫的redo log和undo log來完成端铛。redo log稱為重做日志泣矛,用來保證事務(wù)的原子性和持久性。undo log用來保證事務(wù)的一致性禾蚕。
7.2.1 redo
1.基本概念
重做日志用來實(shí)現(xiàn)事務(wù)的持久性您朽。其右兩部分組成:一是內(nèi)存中的重做日志緩沖(redo log buffer),其是易失的;二是重做日志文件(redo log file)哗总,其是持久的几颜。
InnoDB是事務(wù)的存儲引擎,其通過Force Log at Commit機(jī)制實(shí)現(xiàn)事務(wù)的持久性讯屈,即當(dāng)事務(wù)提交時(shí)蛋哭,必須先將該事務(wù)的所有日志寫入到重做日志文件進(jìn)行持久化,待事務(wù)的commit操作完成才算完成涮母。這里的日志是指重做日志谆趾,在InnoDB存儲引擎中,由兩部分組成叛本,即redo log和undo log沪蓬。redo log用來保證事務(wù)的持久性,undo log用來幫助事務(wù)回滾即MVCC功能来候。redo log 基本上都是順序?qū)懙牧埽跀?shù)據(jù)庫運(yùn)行時(shí)不需要對redo log的文件進(jìn)行讀取操作。而undo log是需要進(jìn)行隨機(jī)讀取的吠勘。
為了確保每次日志都寫入重做日志文件性芬,在每次將重做日志緩沖寫入重做日志文件后,InnoDB存儲引擎都需要調(diào)用一次fsync操作剧防。這是因?yàn)橹刈鋈罩疚募蜷_并沒有使用O_DIRECT選項(xiàng)植锉,因此重做日志緩沖先寫入文件系統(tǒng)緩存。為了確保重做日志寫入磁盤峭拘,必須進(jìn)行一個fsync操作俊庇,由于fsync的效率取決于磁盤的性能鸡挠,所以磁盤的性能決定了事務(wù)提交的性能,也就是數(shù)據(jù)庫的性能彭沼。
參數(shù)innodb_flush_log_at_trx_commit用來控制日志刷新到磁盤的策略。
當(dāng)該參數(shù)值為0時(shí)备埃,表示事務(wù)提交時(shí)不進(jìn)行寫入重做日志的操作姓惑,這個操作僅在Master Thread中完成按脚,而在Master Thread中每1秒會進(jìn)行一次重做日志文件的fsync操作。
當(dāng)該參數(shù)值為1(默認(rèn))時(shí)辅搬,表示事務(wù)提交時(shí)必須調(diào)用一次fsync操作唯沮。
當(dāng)該參數(shù)值為2時(shí),表示事務(wù)提交時(shí)將重做日志寫入重做日志文件,但僅寫入文件系統(tǒng)的緩存中夯缺,不進(jìn)行fsync操作甘耿。在這個設(shè)置下,當(dāng)MySQL數(shù)據(jù)庫發(fā)生宕機(jī)而操作系統(tǒng)不發(fā)生宕機(jī)時(shí)捏境,并不會導(dǎo)致事務(wù)的丟失毁葱。而當(dāng)操作系統(tǒng)宕機(jī)時(shí),重啟數(shù)據(jù)庫后會丟失文件系統(tǒng)緩存刷新到重做日志文件那部分事務(wù)筷频。
雖然用戶可以通過設(shè)置參數(shù)innodb_flush_log_at_trx_commit為0或者2來提高事務(wù)提交的性能前痘,但是需要牢記的是,這種設(shè)置方法喪失了事務(wù)的ACID特性坯癣。
在MySQL數(shù)據(jù)庫中還有一種二進(jìn)制日志(bin log)最欠,其用來進(jìn)行point-in-time的恢復(fù)以及主從復(fù)制(Replication)環(huán)境的建立芝硬。
重做日志和二進(jìn)制日志的區(qū)別是:
首先,重做日志是在InnoDB存儲引擎層產(chǎn)生绍绘,而二進(jìn)制日志是在MySQL數(shù)據(jù)庫上層產(chǎn)生的,并且二進(jìn)制日志不僅僅針對于InnoDB存儲引擎脯倒,MySQL數(shù)據(jù)庫中任何存儲引擎對于數(shù)據(jù)庫的更改都會產(chǎn)生二進(jìn)制日志捺氢。
其次摄乒,兩種日志記錄的內(nèi)容形式不同。MySQL數(shù)據(jù)庫上層的二進(jìn)制日志是一種邏輯日志斋否,其記錄的是對應(yīng)SQL語句拭荤。而InnoDB存儲引擎層面的重做日志是物理格式日志,其記錄的是對于每個頁的修改旦委。
此外雏亚,兩種日志記錄寫入磁盤的時(shí)間點(diǎn)不同,如圖7-6所示查辩。二進(jìn)制日志只在事務(wù)提交完成后進(jìn)行一次寫入网持。而InnoDB存儲引擎的重做日志在事務(wù)進(jìn)行中不斷地被寫入功舀,這表現(xiàn)為日志并不是隨事務(wù)提交的順序進(jìn)行寫入的
2. log block
在InnoDB存儲引擎中,重做日志都是以512字節(jié)進(jìn)行存儲的遣铝。這意味著重做日志緩沖莉擒,重做日志文件都是以塊(block)的方式進(jìn)行保存的,稱之為重做日志塊(redo log block)填硕,每塊都是512字節(jié)鹿鳖。
若一個頁中產(chǎn)生的重做日志數(shù)量大于512字節(jié)翅帜,那么需要分隔為多個重做日志塊進(jìn)行存儲。此外涝滴,由于重做日志塊的大小和磁盤扇區(qū)塊大小一樣,都是512字節(jié)杂抽,因此重做日志的寫入可以保證原子性缩麸,不需要double write技術(shù)。
3.log group
log group為重做日志租愚屁,其中有多個重做日志文件痕檬。log group是一個邏輯上的概念,并沒有一個實(shí)際存儲的物理文件來表示log group 信息梦谜。log group由多個重做日志文件組成,每個log group中日志文件的大小是相同的闭树。重做日志文件中存儲的就是之前在log buffer中保存的log block荒澡,因此其也是根據(jù)塊的方式進(jìn)行物理存儲的管理单山,每個塊的大小與log block一樣,同樣為512字節(jié)昼接。在InnoDB存儲引擎運(yùn)行過程中悴晰,log buffer根據(jù)一定的規(guī)則將內(nèi)存中l(wèi)og block刷新到磁盤。這個規(guī)則就是:
- 事務(wù)提交時(shí)
- 當(dāng)log buffer中有一半的內(nèi)存空間已經(jīng)被使用時(shí)
- log checkpoint 時(shí)
5. LSN
LSN是Log Sequence Number的縮寫漂辐,其代表的是日志序列號髓涯。在InnoDB存儲引擎中饲帅,LSN占用8字節(jié)瘤泪,并且單調(diào)遞增。LSN表示的含義有:
- 重做日志寫入的總量
- checkpoint的位置
- 頁的版本
LSN表示事務(wù)寫入重做日志的字節(jié)的總量赦邻。LSN不僅記錄在重做日志中惶洲,還存在每個頁中。在每個頁的頭部签则,有一個值FIL_PAGE_LSN铐料,記錄了該頁的LSN,在頁中柒凉,LSN表示該頁最后刷新時(shí)LSN的大小篓跛,因?yàn)橹刈鋈罩居涗浀氖敲總€頁的日志愧沟,因此頁中的LSN用來判斷頁是否需要進(jìn)行恢復(fù)操作。例如计盒,頁P(yáng)1的LSN為1000芽丹,而數(shù)據(jù)庫啟動時(shí)拔第,InnoDB檢測到寫入重做日志中的LSN為1300,并且該事務(wù)已經(jīng)提交懈涛,那么數(shù)據(jù)庫需要進(jìn)行恢復(fù)操作泳猬,將重做日志應(yīng)用到P1頁中宇植。同樣的指郁,對于重做日志中LSN小于P1頁的LSN拷呆,不需要進(jìn)行重做,因?yàn)镻1頁的LSN表示頁已經(jīng)刷新到該位置腰懂。
6. 恢復(fù)
InnoDB存儲引擎在啟動時(shí)不管上次數(shù)據(jù)庫運(yùn)行時(shí)是否正常關(guān)閉绣溜,都會嘗試進(jìn)行恢復(fù)操作娄蔼。因?yàn)橹刈鋈罩居涗浀氖俏锢砣罩荆虼嘶謴?fù)的速度比邏輯日志要快得多罢防。由于checkpoint表示已經(jīng)刷新到磁盤上的LSN唉侄,因此在恢復(fù)過程中僅需恢復(fù)checkpoint開始的日志部分属划。
7.2.2 undo
1.基本概念
事務(wù)有時(shí)候需要進(jìn)行回滾操作,這是就需要undo绽昼。因此在對數(shù)據(jù)庫進(jìn)行修改時(shí)须蜗,InnoDB存儲引擎不但會產(chǎn)生redo明肮,還會產(chǎn)生一定量的undo。這樣如果用戶執(zhí)行的事務(wù)或者語句由于某種因?yàn)槭×搜矗只蛘哂靡粭lrollback語句請求回滾秫舌,就可以利用這些undo信息將數(shù)據(jù)回滾到修改之前的樣子。
redo存放在重做日志文件中嫂粟,與redo不同赋元,undo存放在數(shù)據(jù)庫內(nèi)部的一個特殊段(segement)中飒房,這個段稱為undo段(undo segement)狠毯。undo段位于共享表空間內(nèi)。undo是邏輯日志嫡良,因此只是將數(shù)據(jù)庫邏輯地恢復(fù)到原來的樣子献酗。所有修改都被邏輯地取消了罕偎,但是數(shù)據(jù)結(jié)構(gòu)和頁本身在回滾之后可能大不相同。
InnoDB存儲引擎回滾時(shí)甩苛,它實(shí)際上做的是與先前相反的工作俏站。對于每個insert肄扎,innodb存儲引擎會執(zhí)行一個delete;對于每一個delete旭等,innodb存儲引擎會執(zhí)行一個insert雷则;對于每一個update月劈,innodb存儲引擎會執(zhí)行一個相反的update藤乙,將修改前的行放回去坛梁。
除了回滾操作腊凶,undo的另一個作用是MVCC,即在InnoDB存儲引擎中MVCC的實(shí)現(xiàn)是通過undo來完成的褐缠。當(dāng)用戶讀取一行記錄時(shí)队魏,若該行記錄已經(jīng)被其他事務(wù)占用了万搔,當(dāng)前事務(wù)可以通過undo讀取之前的行版本信息瞬雹,以此來實(shí)現(xiàn)非鎖定讀。
undo log會產(chǎn)生redo log呢诬,也就是undo log的產(chǎn)生會伴隨redo log的產(chǎn)生意敛,這是因?yàn)閡ndo log也需要持久性的保護(hù)草姻。
2. undo存儲管理
InnoDB存儲引擎對undo的管理同樣采用段的方式。但是這個段和之前介紹的端有所不同敞曹。首先InnoDB存儲引擎有rollback segement澳迫,每個回滾段中記錄了1024個undo log segement剧劝,而在每個undo log segement段中進(jìn)行段的申請。
事務(wù)在undo log segement分配頁并寫入undo log的這個過程同樣需要寫入重做日志拢锹。當(dāng)事務(wù)提交時(shí)卒稳,InnoDB存儲引擎會做以下兩件事情:
- 將undo log放入列表中,以供之后的purge操作
- 判斷undo log所在的頁是否可以重用减江,若可以分配給下個事務(wù)使用辈灼。
事務(wù)提交后并不能馬上刪除undo log及undo log所在的頁役衡。這是因?yàn)榭赡苓€有其他事務(wù)需要通過undo log來得到行記錄之前的版本薪棒。故事務(wù)提交時(shí)將undo log放入一個鏈表中俐芯,是否可以最終刪除undo log及undo log所在頁有purge線程來判斷。
判斷undo log所在頁是否可以重用的標(biāo)準(zhǔn)是判斷undo頁使用的空間是否小于4/3 邮辽,若是則表示該undo 頁可以被重用吨述,之后新的undo log記錄在當(dāng)前undo log的后面钞脂。
3. undo log格式
在InnoDB存儲引擎中冰啃,undo log分為:
- insert undo log
- update undo log
insert undo log是指在insert操作中產(chǎn)生的undo log,因?yàn)閕nsert操作的記錄焚刚,只對事務(wù)本身可見矿咕,對其他事務(wù)不可見(事務(wù)隔離性的要求),故該undo log可以在事務(wù)提交后直接刪除雌团。不需要進(jìn)行purge操作锦援。
update undo log記錄的是對delete和update操作產(chǎn)生的undo log剥悟。該undo log可能需要提供MVCC機(jī)制,因此不能在事務(wù)提交時(shí)就進(jìn)行刪除略板。提交時(shí)放入undo log鏈表叮称,等待purge線程進(jìn)行最后的刪除藐鹤。
delete操作并不直接刪除記錄娱节,而只是將記錄標(biāo)記為已刪除,也就是將記錄的delete flag 設(shè)置為 1 谴古。而記錄最終的刪除是在purge操作中完成的掰担。
update主鍵的操作其實(shí)分兩步完成怒炸。首先將原主鍵記錄標(biāo)為已刪除横媚,之后再插入一條新的記錄。
7.2.3 purge
delete和update操作可能并不直接刪除原有的數(shù)據(jù)恢口。例如對于delete from t where a = 1;
耕肩,表 t 上列 a 有聚集索引,列 b 上有輔助索引婚被。對于上述delete操作址芯,僅是將主鍵列等于1的記錄delete flag 設(shè)置為 1窜觉,記錄并沒有被刪除禀挫,即記錄還是存在于B+樹中。其次描孟,對于輔助索引上 a 等于 1匿醒,b等于 1 的記錄同樣沒有做任何處理菜职,甚至沒有產(chǎn)生undo log酬核。而真正刪除這行記錄的操作其實(shí)被 "延時(shí)" 了适室,最終在purge操作中完成捣辆。
**7.2.4 group commit **
為了提供 fsync 的效率汽畴,當(dāng)前數(shù)據(jù)庫都提供了 group commit 的功能,即一次fsync可以刷新確保多個事務(wù)日志被寫入文件鲁猩。對于InnoDB存儲引擎來說廓握,事務(wù)提交時(shí)會進(jìn)行兩個階段的操作:
1)修改內(nèi)存中事務(wù)對應(yīng)的信息,并且將日志寫入重做日志緩沖男应。
2)調(diào)用fsync將確保日志都從重做日志緩沖寫入磁盤沐飘。
步驟 2)相對步驟 1)是一個較慢的過程薪铜,這是因?yàn)榇鎯σ嫘枰c磁盤打交道恩溅。當(dāng)有事務(wù)進(jìn)行這個過程時(shí)脚乡,其他事務(wù)可以進(jìn)行步驟 1)的操作,正在提交的事務(wù)完成提交操作后俯艰,再次進(jìn)行步驟 2)锌订,可以將多個事務(wù)的重做日志通過一次fsync刷新到磁盤辆飘,這樣就大大地減少了磁盤的壓力蜈项,從而提高了數(shù)據(jù)庫的整體性能。對于寫入或者更新較為頻繁的操作侥衬,group commit的效果尤為明顯轴总。
7.3 事務(wù)控制語句
在MySQL命令行的默認(rèn)設(shè)置下怀樟,事務(wù)都是自動提交(auto commit)的坡倔,即執(zhí)行SQL語句后就會馬上執(zhí)行commit操作漂佩。因此要顯示地開啟一個事務(wù)需要使用命令BEGIN脖含,START TRANSACTION,或者執(zhí)行命令 SET AUTOCOMMIT = 0投蝉,禁用當(dāng)前會話的自動提交养葵。
事務(wù)控制語句:
- start transaction|begin:顯式的開啟一個事務(wù)。
- commit:提交事務(wù)
- rollback:回滾事務(wù)瘩缆,并撤銷正在進(jìn)行的所有未提交的修改关拒。
- savepoint indentifier:在事務(wù)中創(chuàng)建一個保存點(diǎn)
- release savepoint identifier:刪除一個事務(wù)的保存點(diǎn)
- rollback to identifier:回滾到某個保存點(diǎn)
- set transaction:用來設(shè)置事務(wù)的隔離級別
在存儲過程總只能使用 start transaction 語句來開啟一個事務(wù)
commit和commit work基于基本上是一致的,都是用來提交事務(wù)庸娱。不同之處在于commit work用來控制事務(wù)結(jié)束之后的行為是chain還是release的。如果是chain方式熟尉,那么事務(wù)就變成了鏈?zhǔn)聞?wù)归露。
可以通過參數(shù)completion_type來進(jìn)行控制,該參數(shù)默認(rèn)為0斤儿,表示沒有任何操作剧包,在這種設(shè)置下commit和commit work是完全等價(jià)的。當(dāng)該參數(shù)值為1時(shí)往果,commit work等同于commit and chain疆液,表示馬上自動開啟一個相同隔離級別的事務(wù)。當(dāng)該參數(shù)值為2時(shí)陕贮,commit work等同于commit and release堕油。在事務(wù)提交之后會自動斷開與服務(wù)器的連接。
** 7.4 隱式提交的SQL語句 **
以下這些SQL語句會產(chǎn)生一個隱式的提交操作肮之,即執(zhí)行完這些語句之后掉缺,會有一個隱式的commit操作。
DDL語句:alter database...upgrade data directory name局骤,alter event攀圈,alter procedure,alter table峦甩,alter view,create database现喳,create event凯傲,create index,create procedure嗦篱,create table冰单,create trigger,create view灸促,drop database诫欠,drop event涵卵,drop index,drop procedure荒叼,drop table轿偎,drop trigger,drop view被廓,pename table坏晦,truncate table。
用來隱式地修改MySQL架構(gòu)的操作:create user嫁乘,drop user昆婿,grant,rename user蜓斧,revoke仓蛆,set password
管理語句:analyze table,cache index挎春,check table看疙,load index into cache,optimize table搂蜓,repair table狼荞。
此外,truncate table語句是DDL語句帮碰,雖然和對整張表執(zhí)行delete的結(jié)果是一樣的相味,但它是不能回滾的。