Seata是什么空猜?一文了解其實現(xiàn)原理

一近零、背景

隨著業(yè)務(wù)發(fā)展诺核,單體系統(tǒng)逐漸無法滿足業(yè)務(wù)的需求,分布式架構(gòu)逐漸成為大型互聯(lián)網(wǎng)平臺首選久信。伴隨而來的問題是窖杀,本地事務(wù)方案已經(jīng)無法滿足,分布式事務(wù)相關(guān)規(guī)范和框架應(yīng)運而生裙士。

在這種情況下入客,大型廠商根據(jù)分布式事務(wù)實現(xiàn)規(guī)范,實現(xiàn)了不同的分布式框架腿椎,以簡化業(yè)務(wù)開發(fā)者處理分布式事務(wù)相關(guān)工作桌硫,讓開發(fā)者專注于核心業(yè)務(wù)開發(fā)。

Seata就是這么一個分布式事務(wù)處理框架啃炸,Seata是由阿里開源铆隘,前身為Fescar,經(jīng)過品牌升級變身Seata南用。

二膀钠、分布式事務(wù)規(guī)范

1.分布式事務(wù)相關(guān)概念

事務(wù):一個程序執(zhí)行單元,是用戶定義的一組操作序列裹虫,需要滿足ACID屬性肿嘲。

本地事務(wù):事務(wù)由本地資源管理器管理迹缀。

分布式事務(wù):事務(wù)的操作位于不同的節(jié)點磷雇。

分支事務(wù):在分布式事務(wù)中,由資源管理器管理的本地事務(wù)票腰。

全局事務(wù):一次性操作多個資源管理器完成的事務(wù)匣屡,由一組分支事務(wù)組成封救。

2. 分布式事務(wù)實現(xiàn)規(guī)范

對于本地事務(wù),可以借助DBMS系統(tǒng)來實現(xiàn)事務(wù)的管理捣作,但是對于分布式事務(wù)誉结,它就無能為力了。對于分布式事務(wù)虾宇,目前主要有2種思路:XA協(xié)議的強一致規(guī)范以及柔性事務(wù)的最終一致性規(guī)范。

2.1 XA

XA是基于2階段提交協(xié)議設(shè)計的接口標準如绸,實現(xiàn)了XA規(guī)范的資源管理器就可以參與XA全局事務(wù)嘱朽。應(yīng)用承擔事務(wù)管理器TM工作,數(shù)據(jù)庫承擔資源管理器RM工作怔接,TM生成全局事務(wù)id搪泳,控制RM的提交和回滾。

01.png

2.2 柔性事務(wù)的最終一致性

該規(guī)范主要有3種實現(xiàn)方式扼脐,TCC岸军、MQ事務(wù)消息奋刽、本地消息表。(還存在其他一些不常用實現(xiàn)方式如Saga)艰赞。

TCC:try/confirm/cancel佣谐,在try階段鎖定資源,confirm階段進行提交方妖,資源鎖定失敗執(zhí)行cancel階段釋放資源狭魂。

02.png

MQ事務(wù)消息:前提消息系統(tǒng)需要支持事務(wù)如RocketMQ,在本地事務(wù)執(zhí)行前党觅,發(fā)送事務(wù)消息prepare雌澄,本地事務(wù)執(zhí)行成功,發(fā)送事務(wù)消息commit杯瞻,實現(xiàn)分布式事務(wù)最終一致性镐牺。如果事務(wù)消息commit失敗,RocketMQ會回查消息發(fā)送者確保消息正常提交魁莉,如果步驟5執(zhí)行失敗睬涧,進行重試,達到最終一致性沛厨。

03.png

本地消息表:跟MQ事務(wù)消息類似宙地,區(qū)別在于MQ不支持事務(wù)消息,需要借助本地數(shù)據(jù)庫的事務(wù)管理能力逆皮。在步驟1中將需要發(fā)送的消息和本地事務(wù)一起提交到DB宅粥,借助DB的事務(wù)管理確保消息持久化。步驟2應(yīng)用通過本地消息表掃描电谣,重試發(fā)送秽梅,確保消息可以發(fā)送成功。

04.png

三剿牺、Seata 架構(gòu)

1. ****系統(tǒng)組成

Seata有三個核心組件:

  • Transaction Coordinator(TC企垦,事務(wù)協(xié)調(diào)器)

    維護全局事務(wù)和分支事務(wù)的狀態(tài),驅(qū)動全局事務(wù)提交或回滾晒来。

  • Transaction Manager(TM钞诡,事務(wù)管理器)

    定義全局事務(wù)的范圍,開始事務(wù)湃崩、提交事務(wù)荧降、回滾事務(wù)。

  • Resource Manager(RM攒读,資源管理器):

    管理分支事務(wù)上的資源朵诫,向TC注冊分支事務(wù),匯報分支事務(wù)狀態(tài)薄扁,驅(qū)動分支事務(wù)的提交或回滾剪返。

三個組件相互協(xié)作废累,TC 以 Server 形式獨立部署,TM和RM集成在應(yīng)用中啟動脱盲,其整體交互如下:

05.png

2.工作模式

Seata 支持四種工作模式:

2.1 AT(Auto Transaction)

AT模式是Seata默認的工作模式邑滨。需要基于支持本地 ACID 事務(wù)的關(guān)系型數(shù)據(jù)庫,Java 應(yīng)用宾毒,通過 JDBC 訪問數(shù)據(jù)庫驼修。

2.1.1 整體機制

該模式是XA協(xié)議的演變,XA協(xié)議是基于資源管理器實現(xiàn)诈铛,而AT并不是如此乙各。AT的2個階段分別是:

  • 一階段:業(yè)務(wù)數(shù)據(jù)和回滾日志記錄在同一個本地事務(wù)中提交,釋放本地鎖和連接資源幢竹。

  • 二階段:提交異步化耳峦,非常快速地完成焕毫;回滾通過一階段的回滾日志進行反向補償蹲坷。

下圖中,步驟1開啟全局事務(wù)邑飒;步驟2注冊分支事務(wù)循签,這里對應(yīng)著一階段;步驟3提交或者回滾分支事務(wù)疙咸,對應(yīng)著二階段县匠。

06.png

2.1.2 特點

  • 優(yōu)點:對代碼無侵入;并發(fā)度高撒轮,本地鎖在一階段就會釋放乞旦;不需要數(shù)據(jù)庫對XA協(xié)議的支持。

  • 缺點:只能用在支持ACID的關(guān)系型數(shù)據(jù)庫题山;SQL解析還不能支持全部語法兰粉。

2.2 TCC

該模式工作分為三個階段:prepare/commit/cancel。

2.2.1 整體機制

  • TM向TC申請全局事務(wù)XID顶瞳,傳播給各個子調(diào)用玖姑。

  • 子調(diào)用的所在TM向TC注冊分支事務(wù),并執(zhí)行本地prepare慨菱,并向TC報告執(zhí)行結(jié)果焰络。

  • TC根據(jù)各分支事務(wù)的執(zhí)行結(jié)果確定二階段是執(zhí)行commit或rollback。

07.png

2.2.2 特點

  • 優(yōu)點:不依賴本地事務(wù)抡柿。

  • 缺點:回滾邏輯依賴手動編碼舔琅;業(yè)務(wù)侵入性較大等恐。

2.3 Saga 模式

2.3.1 Saga 是什么洲劣?

1987年普林斯頓大學的Hector Garcia-Molina和Kenneth Salem發(fā)表了一篇Paper Sagas备蚓,講述的是如何處理long lived transaction(長活事務(wù))。Saga是一個長活事務(wù)可被分解成可以交錯運行的子事務(wù)集合囱稽。論文見這里郊尝。

簡單來說,Saga將一個長事務(wù)(T)分解成一系列Sub事務(wù)(Ti)战惊,每個Sub事務(wù)都有對應(yīng)的補償動作(Ci)流昏,用于撤銷Ti事務(wù)產(chǎn)生的影響。Sub事務(wù)是直接提交到庫吞获,在出現(xiàn)異常時况凉,逆向進行補償。

因此Saga事務(wù)的組成有2種:

  • T1, T2, T3, ..., Tn

  • T1, T2, ..., Tj, Cj,..., C2, C1各拷,其中0 < j < n

第一種就是正常提交的情況刁绒,第二種在提交Tj事務(wù)出現(xiàn)異常,開始逆向補償?shù)那闆r烤黍。

Saga模式是Seata提供的長事務(wù)解決方案知市。例如全局事務(wù)中涉及到外部系統(tǒng),無法管理它的資源管理器速蕊,讓它改造成TCC也不好實行嫂丙,這時就可以采用此類方案。

2.3.2 整體機制

在Saga模式中规哲,業(yè)務(wù)流程中每個參與者都提交本地事務(wù)跟啤,當出現(xiàn)某一個參與者失敗則補償前面已經(jīng)成功的參與者,一階段正向服務(wù)和二階段補償服務(wù)都由業(yè)務(wù)開發(fā)實現(xiàn)媳叨。

08.png

上圖中對于多個分支事務(wù)腥光,省略了多次出現(xiàn)的 2.* 步驟。對于全局事務(wù)執(zhí)行過程中業(yè)務(wù)應(yīng)用宕機情況糊秆,業(yè)務(wù)應(yīng)用集群中對等節(jié)點會通過從TC獲取相關(guān)會話武福,從DB加載詳細信息來恢復(fù)狀態(tài)機。

2.3.3 特點

  • 優(yōu)點:一階段提交本地事務(wù)痘番,無鎖捉片,高性能;事件驅(qū)動架構(gòu)汞舱,參與者可異步執(zhí)行伍纫,高吞吐;補償服務(wù)易于實現(xiàn)昂芜。

  • 缺點:不保證隔離性莹规。

2.4 XA模式

XA是基于二階段提交設(shè)計的接口標準。對于支持XA的資源管理器泌神,借助Seata框架的XA模式良漱,會使XA方案更簡單易用舞虱。使用前提:需要分支數(shù)據(jù)庫支持XA 事務(wù),應(yīng)用為 Java應(yīng)用母市,且使用JDBC訪問數(shù)據(jù)庫矾兜。

2.4.1 整體機制

在 Seata 定義的分布式事務(wù)框架內(nèi),利用事務(wù)資源(數(shù)據(jù)庫患久、消息服務(wù)等)對 XA 協(xié)議的支持椅寺,以 XA 協(xié)議的機制來管理分支事務(wù)的一種 事務(wù)模式。

  • 執(zhí)行階段:業(yè)務(wù)sql在XA分支中執(zhí)行蒋失,由分支事務(wù)的RM管理器管理返帕,然后執(zhí)行XA prepare。

  • 完成階段:TM根據(jù)各個分支執(zhí)行結(jié)果通過TC通知各個分支執(zhí)行XA commit或者XA rollback篙挽。

09.png

2.4.2 ****特點

  • 優(yōu)點:繼承了XA協(xié)議的優(yōu)勢溉旋,事務(wù)具有強一致性。

  • 缺點:同樣繼承了XA協(xié)議的劣勢嫉髓,由于分支事務(wù)長時間開啟观腊,并發(fā)度低。

2.5 Seata 各模式對比

分布式事務(wù)方案沒有銀彈算行,根據(jù)自己的業(yè)務(wù)特性選擇合適的模式梧油。例如追求強一致性,可以選擇AT和XA州邢,存在和外部系統(tǒng)對接儡陨,可以選擇Saga模式,不能依賴本地事務(wù)量淌,可以采用TCC等等骗村。結(jié)合各模式的優(yōu)缺點進行選擇。

10.png

四呀枢、AT 模式核心實現(xiàn)

鑒于Seata支持的模式較多胚股,而其默認的模式是AT,為節(jié)省篇幅裙秋,以下圍繞AT模式分析其相關(guān)的核心模塊實現(xiàn)琅拌。

1. 事務(wù)協(xié)調(diào)器的啟動

TC(事務(wù)協(xié)調(diào)器)以獨立的服務(wù)啟動,作為Server摘刑,維護全局事務(wù)和分支事務(wù)的狀態(tài)进宝,驅(qū)動全局事務(wù)提交或回滾。下面是TC的啟動流程:

[圖片上傳失敗...(image-b5010b-1607311250540)]

2. ****事務(wù)管理器的啟動

TM(事務(wù)管理器)集成在應(yīng)用中啟動枷恕,負責定義全局事務(wù)的范圍党晋,開始事務(wù)、提交事務(wù)、回滾事務(wù)未玻。
TM所在應(yīng)用中需要配置GlobalTransactionScannerbean漏益,在應(yīng)用啟動時會進行如下初始化流程:

11.png

3. 資源管理器的啟動

RM(資源管理器)集成在應(yīng)用中啟動,負責管理分支事務(wù)上的資源深胳,向TC注冊分支事務(wù),匯報分支事務(wù)狀態(tài)铜犬,驅(qū)動分支事務(wù)的提交或回滾舞终。
RM所在的應(yīng)用中除了需要跟TM一樣配置GlobalTransactionScanner以啟動RMClient,還需要配置DataSourceProxy癣猾,以實現(xiàn)對數(shù)據(jù)源訪問代理敛劝。該數(shù)據(jù)源代理實現(xiàn)了sql的解析 → 生成undo-log → 業(yè)務(wù)sql和undo-log一并本地提交等操作。

4. 全局事務(wù)的工作流程

下面以一個簡單的例子來說明全局事務(wù)的工作原理:

  • BusinessService:發(fā)起購買服務(wù)

  • StorageService:庫存管理服務(wù)

購買操作實現(xiàn)在businessService.purchase中纷宇,purchase方法實現(xiàn)上通過GlobalTransaction注解夸盟,通過Dubbo服務(wù),調(diào)用了庫存服務(wù)deduct方法方法像捶,樣例如下:

@GlobalTransactional(timeoutMills = 300000, name = "dubbo-demo-tx")
public void purchase(String userId, String commodityCode, int orderCount) {
    storageService.deduct(commodityCode, orderCount);
    // throw new RuntimeException("xxx");
}

4.1 成功的全局事務(wù)處理流程

12.png

4.2 成功的全局事務(wù)處理流程

這里設(shè)定BusinessService在成功調(diào)用StorageService后上陕,本地出現(xiàn)異常。

13.png

5. 寫隔離實現(xiàn)

全局事務(wù)未提交拓春,分支事務(wù)本地已經(jīng)提交的情況下(假設(shè)修改了資源A)释簿,如何避免其他事務(wù)在此時修改資源A?Seata采用全局鎖來實現(xiàn)硼莽,其流程如下:

14.png

6. 讀隔離實現(xiàn)

在數(shù)據(jù)庫本地隔離級別為讀已提交或以上的基礎(chǔ)上庶溶,Seata提供了讀未提交,這個很好理解懂鸵,全局事務(wù)提交前分支事務(wù)本地已經(jīng)提交偏螺。如果想要實現(xiàn)讀已提交,則需要在select語句上加for update匆光。

五套像、總結(jié)

Seata是Java領(lǐng)域很強大的分布式事務(wù)框架,其支持了多種模式终息。其中默認支持的AT模式凉夯,相比于傳統(tǒng)的2PC協(xié)議(基于數(shù)據(jù)庫的XA協(xié)議),很好地解決了2PC長期鎖資源的問題采幌,提高了并發(fā)度劲够。Seata支持的各個模式中,AT模式對業(yè)務(wù)零入侵實現(xiàn)分布式事務(wù)休傍,對于開發(fā)者更加友好征绎。另外Seata的Server在選擇合適的存儲介質(zhì)時可以進行集群模式,減少單點故障影響。

本文主要參考官網(wǎng)和部分博客人柿,同時閱讀了AT模式實現(xiàn)源碼柴墩,如果有不對的地方,望指出凫岖,一起討論交流江咳。

六、參考

作者:vivo官網(wǎng)商城開發(fā)團隊

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末哥放,一起剝皮案震驚了整個濱河市歼指,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌甥雕,老刑警劉巖踩身,帶你破解...
    沈念sama閱讀 219,039評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異社露,居然都是意外死亡挟阻,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,426評論 3 395
  • 文/潘曉璐 我一進店門峭弟,熙熙樓的掌柜王于貴愁眉苦臉地迎上來附鸽,“玉大人,你說我怎么就攤上這事瞒瘸【苎祝” “怎么了?”我有些...
    開封第一講書人閱讀 165,417評論 0 356
  • 文/不壞的土叔 我叫張陵挨务,是天一觀的道長击你。 經(jīng)常有香客問我,道長谎柄,這世上最難降的妖魔是什么丁侄? 我笑而不...
    開封第一講書人閱讀 58,868評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮朝巫,結(jié)果婚禮上鸿摇,老公的妹妹穿的比我還像新娘。我一直安慰自己劈猿,他們只是感情好拙吉,可當我...
    茶點故事閱讀 67,892評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著揪荣,像睡著了一般筷黔。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上仗颈,一...
    開封第一講書人閱讀 51,692評論 1 305
  • 那天佛舱,我揣著相機與錄音,去河邊找鬼。 笑死请祖,一個胖子當著我的面吹牛订歪,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播肆捕,決...
    沈念sama閱讀 40,416評論 3 419
  • 文/蒼蘭香墨 我猛地睜開眼刷晋,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了慎陵?” 一聲冷哼從身側(cè)響起眼虱,我...
    開封第一講書人閱讀 39,326評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎荆姆,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體映凳,經(jīng)...
    沈念sama閱讀 45,782評論 1 316
  • 正文 獨居荒郊野嶺守林人離奇死亡胆筒,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,957評論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了诈豌。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片仆救。...
    茶點故事閱讀 40,102評論 1 350
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖矫渔,靈堂內(nèi)的尸體忽然破棺而出彤蔽,到底是詐尸還是另有隱情,我是刑警寧澤庙洼,帶...
    沈念sama閱讀 35,790評論 5 346
  • 正文 年R本政府宣布顿痪,位于F島的核電站,受9級特大地震影響油够,放射性物質(zhì)發(fā)生泄漏蚁袭。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,442評論 3 331
  • 文/蒙蒙 一石咬、第九天 我趴在偏房一處隱蔽的房頂上張望揩悄。 院中可真熱鬧,春花似錦鬼悠、人聲如沸删性。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,996評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽蹬挺。三九已至,卻和暖如春它掂,著一層夾襖步出監(jiān)牢的瞬間汗侵,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,113評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留晰韵,地道東北人发乔。 一個月前我還...
    沈念sama閱讀 48,332評論 3 373
  • 正文 我出身青樓,卻偏偏與公主長得像雪猪,于是被迫代替她去往敵國和親栏尚。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 45,044評論 2 355

推薦閱讀更多精彩內(nèi)容