Fescar锁和隔离级别的理解
Fescar全局鎖的理解
前幾天夜里,我老大發(fā)我一篇文章說阿里的GTS開源了。 因為一直對分布式事務(wù)比較感興趣,立馬pull了代碼,進行閱讀。基本的原理,實現(xiàn)方案我就不一一細化了,詳細見官方文檔(寫的很棒,點贊)。
在fescar的社區(qū),大家比較關(guān)注的是通過fescar回滾到before快照前,別的線程假如更新了數(shù)據(jù),且業(yè)務(wù)走完了,那么恢復(fù)的這個快照不就是臟數(shù)據(jù)了么。 很顯然,這種情況在fescar中是不被允許的。
那么fescar是如何做的呢?
我們先簡單了解一下fescar的設(shè)計原理
那些一上來就喜歡看源碼的同學(xué),一定不要錯過這么官方的圖文介紹,看完再讀源碼事半功倍。
Fescar官方介紹(https://github.com/alibaba/fescar/wiki)
了解完Fescar的基本原理,我們重點關(guān)注下Fescar的全局排他鎖
Fescar設(shè)計了一個全局的排他鎖,來保證事務(wù)間的 寫隔離。
關(guān)于隔離性:(這是Fescar官方給的一段話)
全局事務(wù)的隔離性是建立在分支事務(wù)的本地隔離級別基礎(chǔ)之上的。
在數(shù)據(jù)庫本地隔離級別 讀已提交或以上 的前提下,Fescar 設(shè)計了由事務(wù)協(xié)調(diào)器維護的 全局寫排他鎖,來保證事務(wù)間的 寫隔離,將 全局事務(wù)默認定義在 讀未提交 的隔離級別上。
我們對隔離級別的共識是:絕大部分應(yīng)用在讀已提交的隔離級別下工作是沒有問題的。而實際上,這當(dāng)中又有絕大多數(shù)的應(yīng)用場景,實際上工作在讀未提交的隔離級別下同樣沒有問題。
在極端場景下,應(yīng)用如果需要達到全局的讀已提交,Fescar也提供了相應(yīng)的機制來達到目的。 默認,Fescar 是工作在 讀無提交 的隔離級別下,保證絕大多數(shù)場景的高效性。
我的解讀
本地事務(wù)【讀已提交】,fescar全局事務(wù)【讀未提交】。這是這段話的核心。 我理解的這段話中fescar全局事務(wù)讀未提交,并不是說本地事務(wù)的db數(shù)據(jù)沒有正常提交,而是指全局事務(wù)二階段commit|rollback未真正處理完(即未釋放全局鎖)。
總結(jié)來說:全局未提交但是本地已提交的數(shù)據(jù),對其他全局事務(wù)是可見的【當(dāng)然在本地事務(wù)提交后,本地事務(wù)提交前,隔離級別是本地事務(wù)的管轄范圍】
for example 產(chǎn)品份額有5W,A用戶購買了2萬,份額branch一階段完畢(本地事務(wù)份額已經(jīng)扣除commit),但是在下單的時候異常了。 因為本地事務(wù)讀已提交,這時候fescar允許業(yè)務(wù)訪問該條數(shù)據(jù),3W,在A用戶的份額branch未回滾成功前,對其他用戶可見。 但是其他用戶并不能買該產(chǎn)品,必須等到產(chǎn)品份額回滾到5萬,其他用戶才可以操作產(chǎn)品數(shù)據(jù)。
所以看了這個例子 真的有必要做到全局事務(wù)讀已提交么?
我們先來看一下Fescar的全局鎖的做法
Fescar一階段
1. 本地(Branch)在向TC注冊的時候,把本地事務(wù)需要修改的數(shù)據(jù)table+pks提交到server端申請鎖,拿到全局鎖后,才能提交本地事務(wù)
2. 全局鎖的結(jié)構(gòu):resourceId + table + pks
3. 鎖是存在server端 branchSession中
Fescar二階段
一階段本地事務(wù)提交,db的鎖釋放了(for update鎖),但是全局鎖繼續(xù)保持, 直到二階段決議(注意釋放鎖的順序):
1. 提交:TC 釋放鎖,通知branch提交后 (rm端異步處理)
2. 回滾:TC 通知branch回滾后,釋放鎖(rm端同步處理 執(zhí)行undo_log)
Fescar如何保障鎖的高效?
大家自己先思考下,最后給大家仔細解讀官方的demo,并分析fescar的性能問題。
Fescar目前開源版本全局鎖的實現(xiàn)
大家有興趣自己閱讀:com.alibaba.fescar.server.lock.DefaultLockManagerImpl
官方的圖實在是做的太漂亮了,clone一份解讀 TC TM RM 以及全局鎖的獲取和釋放動作發(fā)生點
分支事務(wù)如何工作?關(guān)注全局鎖的獲取和釋放 特別是二階段commit和rollback全局鎖釋放的順序
Fescar中 RM TM TC如何工作的?
看了這兩張圖,大家應(yīng)該對fescar是如何工作的應(yīng)該有一個大致的了解了。?
1. 全局鎖的獲取
2. tm tc rm之間如何通信工作
3. 隔離級別問題的思考
最后我們來解讀一遍官方的demo
branch1:update storage
tbl set count = count - ? where commoditycode = ?branch2:update account
tbl set money = money - ? where userid = ?branch3:insert into order
tbl (userid, commodity_code, count, money) values (?, ?, ?, ?)
1. 線程A:執(zhí)行branch1(pk:55),執(zhí)行branch2的時候發(fā)現(xiàn)沒錢了,扔了一個異常,那么勢必需要回滾branch1的份額。
TM通知TC開始回滾branch1份額中
2. 線程B:執(zhí)行branch1(pk:55)
如果線程A中branch1(pk:55)已經(jīng)回滾成功了,那么B線程可以正常拿到鎖走下去
如果線程A中branch1還未回滾(resourceId+table+pk鎖未釋放)。當(dāng)線程B發(fā)起branch1向server發(fā)起申請鎖,會直接失敗。
Fescar全局鎖簡單總結(jié):操作一條記錄的分支事務(wù),必須等待這條記錄的前一個分支事務(wù)執(zhí)行結(jié)束(具體commit rollback情況分析如下),才能持有鎖。
其實相比XA的鎖,fescar在每個分支事務(wù)的一階段結(jié)束后都釋放了db的鎖,所以fescar的性能瓶頸應(yīng)該在于二階段的執(zhí)行速度(釋放鎖的快慢)
因為分布式事務(wù)在執(zhí)行事務(wù)編排前,一般會校驗業(yè)務(wù)的正確性,所以發(fā)生回滾的概率相對較低,所以先考慮二階段commit操作。
1. Commit場景分析:
TM通知server進行commit,server立馬釋 branch的鎖,然后再逐個通知RM提交 消耗:1 rpc操作,(branch刪除undo_log放在異步隊列里面做)
2. Rollback場景分析:
TM通知server進行rollback,server通知RM回滾后立馬釋放 branch的鎖。 消耗:1 + N的rpc操作 + N的回滾sql操作
所以總的來看fescar在commit的釋放全局鎖還是非常高效的。
思考
1. server支持多臺機器部署,應(yīng)該如何改造?
全局鎖的問題,鎖改造; 全局事務(wù)向server0申請的,Branch1發(fā)到server1,branch2發(fā)到server2的問題,多機器恢復(fù)的情況,TC的改造
2. 全局鎖在Fescar中更新確實是沒有問題的,但是如果就是業(yè)務(wù)方需要手動調(diào)整DB數(shù)據(jù)呢 ?
大膽猜測,依賴Fescar寫了一個管理平臺 用來執(zhí)行sql的。哈哈
3. 隔離級別的思考
Fescar默認工作在,本地事務(wù)讀已提交,全局事務(wù)讀未提交。 是否存在全局事務(wù)必須工作在【讀已提交】級別而不能工作在【讀未提交】的業(yè)務(wù)場景呢? 大家大膽腦洞 這個問題值得探討。
4. Fescar的文檔中說,是支持全局事務(wù)讀已提交的,那么fescar是如何實現(xiàn)的呢?
感興趣的同學(xué)可以試著讀一下
com.alibaba.fescar.rm.datasource.exec.SelectForUpdateExecutor復(fù)制代碼源碼核心類
大家想讀源碼的話,可以重點關(guān)注一下幾個類。有問題一起探討。
TM相關(guān)
com.alibaba.fescar.tm.api.TransactionalTemplate 復(fù)制代碼RM相關(guān)
TC相關(guān)
- Github:https://github.com/alibaba/fescar
- 官方中文介紹:https://github.com/alibaba/fescar/wiki
作者簡介
雨人,銅板街交易團隊研發(fā)工程師,2016年5月加入銅板街,目前主要負責(zé)資金端項目的開發(fā)。
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ??
? ? ? ? ? ? ? ? ? ? ? 更多精彩內(nèi)容,請掃碼關(guān)注 “銅板街技術(shù)” 微信公眾號。?
總結(jié)
以上是生活随笔為你收集整理的Fescar锁和隔离级别的理解的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: x64位寄存器名称
- 下一篇: 【Linux】rpm常用命令及rpm参数