www.久久久久|狼友网站av天堂|精品国产无码a片|一级av色欲av|91在线播放视频|亚洲无码主播在线|国产精品草久在线|明星AV网站在线|污污内射久久一区|婷婷综合视频网站

當(dāng)前位置:首頁(yè) > 公眾號(hào)精選 > 架構(gòu)師社區(qū)
[導(dǎo)讀]本來(lái)不知道寫點(diǎn)啥,正好手頭有個(gè)新項(xiàng)目試著用阿里的Seata中間件做分布式事務(wù),那就做一個(gè)實(shí)踐分享吧!

本來(lái)不知道寫點(diǎn)啥,正好手頭有個(gè)新項(xiàng)目試著用阿里的 Seata 中間件做分布式事務(wù),那就做一個(gè)實(shí)踐分享吧!

介紹 Seata 之前在簡(jiǎn)單回顧一下分布式事務(wù)的基本概念。

分布式事務(wù)的產(chǎn)生

我們先看看百度上對(duì)于分布式事務(wù)的定義:分布式事務(wù)是指事務(wù)的參與者、支持事務(wù)的服務(wù)器、資源服務(wù)器以及事務(wù)管理器分別位于不同的分布式系統(tǒng)的不同節(jié)點(diǎn)之上。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

額~ 有點(diǎn)抽象,簡(jiǎn)單的畫個(gè)圖好理解一下,拿下單減庫(kù)存、扣余額來(lái)說(shuō)舉例:

當(dāng)系統(tǒng)的體量很小時(shí),單體架構(gòu)完全可以滿足現(xiàn)有業(yè)務(wù)需求,所有的業(yè)務(wù)共用一個(gè)數(shù)據(jù)庫(kù),整個(gè)下單流程或許只用在一個(gè)方法里同一個(gè)事務(wù)下操作數(shù)據(jù)庫(kù)即可。此時(shí)做到所有操作要么全部提交 或 要么全部回滾很容易。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

分庫(kù)分表、SOA

可隨著業(yè)務(wù)量的不斷增長(zhǎng),單體架構(gòu)漸漸扛不住巨大的流量,此時(shí)就需要對(duì)數(shù)據(jù)庫(kù)、表做 分庫(kù)分表處理,將應(yīng)用 SOA 服務(wù)化拆分。也就產(chǎn)生了訂單中心、用戶中心、庫(kù)存中心等,由此帶來(lái)的問(wèn)題就是業(yè)務(wù)間相互隔離,每個(gè)業(yè)務(wù)都維護(hù)著自己的數(shù)據(jù)庫(kù),數(shù)據(jù)的交換只能進(jìn)行 RPC 調(diào)用。

當(dāng)用戶再次下單時(shí),需同時(shí)對(duì)訂單庫(kù) order、庫(kù)存庫(kù) storage、用戶庫(kù) account 進(jìn)行操作,可此時(shí)我們只能保證自己本地的數(shù)據(jù)一致性,無(wú)法保證調(diào)用其他服務(wù)的操作是否成功,所以為了保證整個(gè)下單流程的數(shù)據(jù)一致性,就需要分布式事務(wù)介入。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

Seata 優(yōu)勢(shì)

實(shí)現(xiàn)分布式事務(wù)的方案比較多,常見(jiàn)的比如基于 XA 協(xié)議的 2PC、3PC,基于業(yè)務(wù)層的 TCC,還有應(yīng)用消息隊(duì)列 + 消息表實(shí)現(xiàn)的最終一致性方案,還有今天要說(shuō)的 Seata 中間件,下邊看看各個(gè)方案的優(yōu)缺點(diǎn)。

2PC

基于 XA 協(xié)議實(shí)現(xiàn)的分布式事務(wù),XA 協(xié)議中分為兩部分:事務(wù)管理器和本地資源管理器。其中本地資源管理器往往由數(shù)據(jù)庫(kù)實(shí)現(xiàn),比如 Oracle、MYSQL 這些數(shù)據(jù)庫(kù)都實(shí)現(xiàn)了 XA 接口,而事務(wù)管理器則作為一個(gè)全局的調(diào)度者。

兩階段提交(2PC),對(duì)業(yè)務(wù)侵?很小,它最?的優(yōu)勢(shì)就是對(duì)使??透明,用戶可以像使?本地事務(wù)?樣使?基于 XA 協(xié)議的分布式事務(wù),能夠嚴(yán)格保障事務(wù) ACID 特性。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

2PC的缺點(diǎn)也是顯而易見(jiàn),它是一個(gè)強(qiáng)一致性的同步阻塞協(xié)議,事務(wù)執(zhí)?過(guò)程中需要將所需資源全部鎖定,也就是俗稱的 剛性事務(wù)。所以它比較適?于執(zhí)?時(shí)間確定的短事務(wù),整體性能比較差。

一旦事務(wù)協(xié)調(diào)者宕機(jī)或者發(fā)生網(wǎng)絡(luò)抖動(dòng),會(huì)讓參與者一直處于鎖定資源的狀態(tài)或者只有一部分參與者提交成功,導(dǎo)致數(shù)據(jù)的不一致。因此,在?并發(fā)性能?上的場(chǎng)景中,基于 XA 協(xié)議的分布式事務(wù)并不是最佳選擇。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

3PC

三段提交(3PC)是二階段提交(2PC)的一種改進(jìn)版本 ,為解決兩階段提交協(xié)議的阻塞問(wèn)題,上邊提到兩段提交,當(dāng)協(xié)調(diào)者崩潰時(shí),參與者不能做出最后的選擇,就會(huì)一直保持阻塞鎖定資源。

2PC 中只有協(xié)調(diào)者有超時(shí)機(jī)制,3PC 在協(xié)調(diào)者和參與者中都引入了超時(shí)機(jī)制,協(xié)調(diào)者出現(xiàn)故障后,參與者就不會(huì)一直阻塞。而且在第一階段和第二階段中又插入了一個(gè)準(zhǔn)備階段(如下圖,看著有點(diǎn)啰嗦),保證了在最后提交階段之前各參與節(jié)點(diǎn)的狀態(tài)是一致的。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

雖然 3PC 用超時(shí)機(jī)制,解決了協(xié)調(diào)者故障后參與者的阻塞問(wèn)題,但與此同時(shí)卻多了一次網(wǎng)絡(luò)通信,性能上反而變得更差,也不太推薦。

TCC

所謂的 TCC 編程模式,也是兩階段提交的一個(gè)變種,不同的是 TCC 為在業(yè)務(wù)層編寫代碼實(shí)現(xiàn)的兩階段提交。TCC 分別指 TryConfirm、Cancel ,一個(gè)業(yè)務(wù)操作要對(duì)應(yīng)的寫這三個(gè)方法。

以下單扣庫(kù)存為例,Try 階段去占庫(kù)存,Confirm 階段則實(shí)際扣庫(kù)存,如果庫(kù)存扣減失敗 Cancel 階段進(jìn)行回滾,釋放庫(kù)存。

TCC 不存在資源阻塞的問(wèn)題,因?yàn)槊總€(gè)方法都直接進(jìn)行事務(wù)的提交,一旦出現(xiàn)異常通過(guò)則 Cancel 來(lái)進(jìn)行回滾補(bǔ)償,這也就是常說(shuō)的補(bǔ)償性事務(wù)。

原本一個(gè)方法,現(xiàn)在卻需要三個(gè)方法來(lái)支持,可以看到 TCC 對(duì)業(yè)務(wù)的侵入性很強(qiáng),而且這種模式并不能很好地被復(fù)用,會(huì)導(dǎo)致開(kāi)發(fā)量激增。還要考慮到網(wǎng)絡(luò)波動(dòng)等原因,為保證請(qǐng)求一定送達(dá)都會(huì)有重試機(jī)制,所以考慮到接口的冪等性。

消息事務(wù)(最終一致性)

消息事務(wù)其實(shí)就是基于消息中間件的兩階段提交,將本地事務(wù)和發(fā)消息放在同一個(gè)事務(wù)里,保證本地操作和發(fā)送消息同時(shí)成功。下單扣庫(kù)存原理圖:

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
  • 訂單系統(tǒng)向 MQ 發(fā)送一條預(yù)備扣減庫(kù)存消息, MQ 保存預(yù)備消息并返回成功 ACK
  • 接收到預(yù)備消息執(zhí)行成功 ACK,訂單系統(tǒng)執(zhí)行本地下單操作,為防止消息發(fā)送成功而本地事務(wù)失敗,訂單系統(tǒng)會(huì)實(shí)現(xiàn) MQ 的回調(diào)接口,其內(nèi)不斷的檢查本地事務(wù)是否執(zhí)行成功,如果失敗則 rollback 回滾預(yù)備消息;成功則對(duì)消息進(jìn)行最終 commit 提交。
  • 庫(kù)存系統(tǒng)消費(fèi)扣減庫(kù)存消息,執(zhí)行本地事務(wù),如果扣減失敗,消息會(huì)重新投,一旦超出重試次數(shù),則本地表持久化失敗消息,并啟動(dòng)定時(shí)任務(wù)做補(bǔ)償。

基于消息中間件的兩階段提交方案,通常用在高并發(fā)場(chǎng)景下使用,犧牲數(shù)據(jù)的強(qiáng)一致性換取性能的大幅提升,不過(guò)實(shí)現(xiàn)這種方式的成本和復(fù)雜度是比較高的,還要看實(shí)際業(yè)務(wù)情況。

Seata

Seata 也是從兩段提交演變而來(lái)的一種分布式事務(wù)解決方案,提供了 AT、TCCSAGAXA 等事務(wù)模式,這里重點(diǎn)介紹 AT模式。

既然 Seata 是兩段提交,那我們看看它在每個(gè)階段都做了點(diǎn)啥?下邊我們還以下單扣庫(kù)存、扣余額舉例。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

先介紹 Seata 分布式事務(wù)的幾種角色:

  • Transaction Coordinator(TC): ?全局事務(wù)協(xié)調(diào)者,用來(lái)協(xié)調(diào)全局事務(wù)和各個(gè)分支事務(wù)(不同服務(wù))的狀態(tài), 驅(qū)動(dòng)全局事務(wù)和各個(gè)分支事務(wù)的回滾或提交。

  • Transaction Manager?: ?事務(wù)管理者,業(yè)務(wù)層中用來(lái)開(kāi)啟/提交/回滾一個(gè)整體事務(wù)(在調(diào)用服務(wù)的方法中用注解開(kāi)啟事務(wù))。

  • Resource Manager(RM): ?資源管理者,一般指業(yè)務(wù)數(shù)據(jù)庫(kù)代表了一個(gè)分支事務(wù)(Branch Transaction),管理分支事務(wù)與 TC 進(jìn)行協(xié)調(diào)注冊(cè)分支事務(wù)并且匯報(bào)分支事務(wù)的狀態(tài),驅(qū)動(dòng)分支事務(wù)的提交或回滾。

Seata 實(shí)現(xiàn)分布式事務(wù),設(shè)計(jì)了一個(gè)關(guān)鍵角色 UNDO_LOG (回滾日志記錄表),我們?cè)诿總€(gè)應(yīng)用分布式事務(wù)的業(yè)務(wù)庫(kù)中創(chuàng)建這張表,這個(gè)表的核心作用就是,將業(yè)務(wù)數(shù)據(jù)在更新前后的數(shù)據(jù)鏡像組織成回滾日志,備份在 UNDO_LOG 表中,以便業(yè)務(wù)異常能隨時(shí)回滾。

第一個(gè)階段

比如:下邊我們更新 user 表的 name 字段。

update?user?set?name?=?'小富最帥'?where?name?=?'程序員內(nèi)點(diǎn)事'

首先 Seata 的 JDBC 數(shù)據(jù)源代理通過(guò)對(duì)業(yè)務(wù) SQL 解析,提取 SQL 的元數(shù)據(jù),也就是得到 SQL 的類型(UPDATE),表(user),條件(where name = '程序員內(nèi)點(diǎn)事')等相關(guān)的信息。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
第一個(gè)階段的流程圖

先查詢數(shù)據(jù)前鏡像,根據(jù)解析得到的條件信息,生成查詢語(yǔ)句,定位一條數(shù)據(jù)。

select??name?from?user?where?name?=?'程序員內(nèi)點(diǎn)事'
對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
數(shù)據(jù)前鏡像

緊接著執(zhí)行業(yè)務(wù) SQL,根據(jù)前鏡像數(shù)據(jù)主鍵查詢出后鏡像數(shù)據(jù)

select?name?from?user?where?id?=?1
對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
數(shù)據(jù)后鏡像

把業(yè)務(wù)數(shù)據(jù)在更新前后的數(shù)據(jù)鏡像組織成回滾日志,將業(yè)務(wù)數(shù)據(jù)的更新和回滾日志在同一個(gè)本地事務(wù)中提交,分別插入到業(yè)務(wù)表和 UNDO_LOG 表中。

回滾記錄數(shù)據(jù)格式如下:包括 afterImage 前鏡像、beforeImage 后鏡像、 branchId 分支事務(wù)ID、xid 全局事務(wù)ID

{
????"branchId":641789253,
????"xid":"xid:xxx",
????"undoItems":[
????????{
????????????"afterImage":{
????????????????"rows":[
????????????????????{
????????????????????????"fields":[
????????????????????????????{
????????????????????????????????"name":"id",
????????????????????????????????"type":4,
????????????????????????????????"value":1
????????????????????????????}
????????????????????????]
????????????????????}
????????????????],
????????????????"tableName":"product"
????????????},
????????????"beforeImage":{
????????????????"rows":[
????????????????????{
????????????????????????"fields":[
????????????????????????????{
????????????????????????????????"name":"id",
????????????????????????????????"type":4,
????????????????????????????????"value":1
????????????????????????????}
????????????????????????]
????????????????????}
????????????????],
????????????????"tableName":"product"
????????????},
????????????"sqlType":"UPDATE"
????????}
????]
}

這樣就可以保證,任何提交的業(yè)務(wù)數(shù)據(jù)的更新一定有相應(yīng)的回滾日志。

在本地事務(wù)提交前,各分支事務(wù)需向 全局事務(wù)協(xié)調(diào)者 TC 注冊(cè)分支 ( Branch Id) ,為要修改的記錄申請(qǐng) 全局鎖 ,要為這條數(shù)據(jù)加鎖,利用 SELECT FOR UPDATE 語(yǔ)句。而如果一直拿不到鎖那就需要回滾本地事務(wù)。TM 開(kāi)啟事務(wù)后會(huì)生成全局唯一的 XID,會(huì)在各個(gè)調(diào)用的服務(wù)間進(jìn)行傳遞。

有了這樣的機(jī)制,本地事務(wù)分支(Branch Transaction)便可以在全局事務(wù)的第一階段提交,并馬上釋放本地事務(wù)鎖定的資源。相比于傳統(tǒng)的 XA 事務(wù)在第二階段釋放資源,Seata 降低了鎖范圍提高效率,即使第二階段發(fā)生異常需要回滾,也可以快速 從UNDO_LOG 表中找到對(duì)應(yīng)回滾數(shù)據(jù)并反解析成 SQL 來(lái)達(dá)到回滾補(bǔ)償。

最后本地事務(wù)提交,業(yè)務(wù)數(shù)據(jù)的更新和前面生成的 UNDO LOG 數(shù)據(jù)一并提交,并將本地事務(wù)提交的結(jié)果上報(bào)給全局事務(wù)協(xié)調(diào)者 TC。

第二個(gè)階段

第二階段是根據(jù)各分支的決議做提交或回滾:

如果決議是全局提交,此時(shí)各分支事務(wù)已提交并成功,這時(shí) 全局事務(wù)協(xié)調(diào)者(TC) 會(huì)向分支發(fā)送第二階段的請(qǐng)求。收到 TC 的分支提交請(qǐng)求,該請(qǐng)求會(huì)被放入一個(gè)異步任務(wù)隊(duì)列中,并馬上返回提交成功結(jié)果給 TC。異步隊(duì)列中會(huì)異步和批量地根據(jù) Branch ID 查找并刪除相應(yīng) UNDO LOG 回滾記錄。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

如果決議是全局回滾,過(guò)程比全局提交麻煩一點(diǎn),RM 服務(wù)方收到 TC 全局協(xié)調(diào)者發(fā)來(lái)的回滾請(qǐng)求,通過(guò) XIDBranch ID 找到相應(yīng)的回滾日志記錄,通過(guò)回滾記錄生成反向的更新 SQL 并執(zhí)行,以完成分支的回滾。

注意:這里刪除回滾日志記錄操作,一定是在本地業(yè)務(wù)事務(wù)執(zhí)行之后

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

上邊說(shuō)了幾種分布式事務(wù)各自的優(yōu)缺點(diǎn),下邊實(shí)踐一下分布式事務(wù)中間 Seata 感受一下。

Seata 實(shí)踐

Seata 是一個(gè)需獨(dú)立部署的中間件,所以先搭 Seata Server,這里以最新的 seata-server-1.4.0 版本為例,下載地址:https://seata.io/en-us/blog/download.html

解壓后的文件我們只需要關(guān)心 \seata\conf 目錄下的 file.conf 和 ?registry.conf 文件。

Seata Server

file.conf

file.conf 文件用于配置持久化事務(wù)日志的模式,目前提供 file、dbredis 三種方式。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
file.conf 文件配置

注意:在選擇 db 方式后,需要在對(duì)應(yīng)數(shù)據(jù)庫(kù)創(chuàng)建 globalTable(持久化全局事務(wù))、branchTable(持久化各提交分支的事務(wù))、 lockTable(持久化各分支鎖定資源事務(wù))三張表。

--?the?table?to?store?GlobalSession?data
--?持久化全局事務(wù)
CREATE?TABLE?IF?NOT?EXISTS?`global_table`
(
????`xid`???????????????????????VARCHAR(128)?NOT?NULL,
????`transaction_id`????????????BIGINT,
????`status`????????????????????TINYINT??????NOT?NULL,
????`application_id`????????????VARCHAR(32),
????`transaction_service_group`?VARCHAR(32),
????`transaction_name`??????????VARCHAR(128),
????`timeout`???????????????????INT,
????`begin_time`????????????????BIGINT,
????`application_data`??????????VARCHAR(2000),
????`gmt_create`????????????????DATETIME,
????`gmt_modified`??????????????DATETIME,
????PRIMARY?KEY?(`xid`),
????KEY?`idx_gmt_modified_status`?(`gmt_modified`,?`status`),
????KEY?`idx_transaction_id`?(`transaction_id`)
)?ENGINE?=?InnoDB
??DEFAULT?CHARSET?=?utf8;

--?the?table?to?store?BranchSession?data
--?持久化各提交分支的事務(wù)
CREATE?TABLE?IF?NOT?EXISTS?`branch_table`
(
????`branch_id`?????????BIGINT???????NOT?NULL,
????`xid`???????????????VARCHAR(128)?NOT?NULL,
????`transaction_id`????BIGINT,
????`resource_group_id`?VARCHAR(32),
????`resource_id`???????VARCHAR(256),
????`branch_type`???????VARCHAR(8),
????`status`????????????TINYINT,
????`client_id`?????????VARCHAR(64),
????`application_data`??VARCHAR(2000),
????`gmt_create`????????DATETIME(6),
????`gmt_modified`??????DATETIME(6),
????PRIMARY?KEY?(`branch_id`),
????KEY?`idx_xid`?(`xid`)
)?ENGINE?=?InnoDB
??DEFAULT?CHARSET?=?utf8;

--?the?table?to?store?lock?data
--?持久化每個(gè)分支鎖表事務(wù)
CREATE?TABLE?IF?NOT?EXISTS?`lock_table`
(
????`row_key`????????VARCHAR(128)?NOT?NULL,
????`xid`????????????VARCHAR(96),
????`transaction_id`?BIGINT,
????`branch_id`??????BIGINT???????NOT?NULL,
????`resource_id`????VARCHAR(256),
????`table_name`?????VARCHAR(32),
????`pk`?????????????VARCHAR(36),
????`gmt_create`?????DATETIME,
????`gmt_modified`???DATETIME,
????PRIMARY?KEY?(`row_key`),
????KEY?`idx_branch_id`?(`branch_id`)
)?ENGINE?=?InnoDB
??DEFAULT?CHARSET?=?utf8;

registry.conf

registry.conf 文件設(shè)置 注冊(cè)中心 和 配置中心:

目前注冊(cè)中心支持 nacos 、eureka、redis、zk、consul、etcd3、sofa 七種,這里我使用的 eureka作為注冊(cè)中心 ;配置中心支持 nacosapollo、zkconsul、etcd3 五種方式。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
registry.conf 文件配置

配置完以后在 \seata\bin 目錄下啟動(dòng) seata-server 即可,到這 Seata 的服務(wù)端就搭建好了。

Seata Client

Seata Server 環(huán)境搭建完,接下來(lái)我們新建三個(gè)服務(wù) order-server(下單服務(wù))、storage-server(扣減庫(kù)存服務(wù))、account-server(賬戶金額服務(wù)),分別服務(wù)注冊(cè)到 eureka。

每個(gè)服務(wù)的大體核心配置如下:

spring:
????application:
????????name:?storage-server
????cloud:
????????alibaba:
????????????seata:
????????????????tx-service-group:?my_test_tx_group
????datasource:
????????driver-class-name:?com.mysql.jdbc.Driver
????????url:?jdbc:mysql://47.93.6.1:3306/seat-storage
????????username:?root
????????password:?root

#?eureka?注冊(cè)中心
eureka:
????client:
????????serviceUrl:
????????????defaultZone:?http://$
{eureka.instance.hostname}:8761/eureka/
????instance:
????????hostname:?47.93.6.5
????????prefer-ip-address:?true

業(yè)務(wù)大致流程:用戶發(fā)起下單請(qǐng)求,本地 order 訂單服務(wù)創(chuàng)建訂單記錄,并通過(guò) RPC 遠(yuǎn)程調(diào)用 storage 扣減庫(kù)存服務(wù)和 account 扣賬戶余額服務(wù),只有三個(gè)服務(wù)同時(shí)執(zhí)行成功,才是一個(gè)完整的下單流程。如果某個(gè)服執(zhí)行失敗,則其他服務(wù)全部回滾。

Seata 對(duì)業(yè)務(wù)代碼的侵入性非常小,代碼中使用只需用 @GlobalTransactional 注解開(kāi)啟一個(gè)全局事務(wù)即可。

@Override
@GlobalTransactional(name?=?"create-order",?rollbackFor?=?Exception.class)
public?void?create(Order?order)?
{

????String?xid?=?RootContext.getXID();

????LOGGER.info("------->交易開(kāi)始");
????//本地方法
????orderDao.create(order);

????//遠(yuǎn)程方法?扣減庫(kù)存
????storageApi.decrease(order.getProductId(),?order.getCount());

????//遠(yuǎn)程方法?扣減賬戶余額
????LOGGER.info("------->扣減賬戶開(kāi)始o(jì)rder中");
????accountApi.decrease(order.getUserId(),?order.getMoney());
????LOGGER.info("------->扣減賬戶結(jié)束order中");

????LOGGER.info("------->交易結(jié)束");
????LOGGER.info("全局事務(wù) xid:?{}",?xid);
}

前邊說(shuō)過(guò) Seata AT 模式實(shí)現(xiàn)分布式事務(wù),必須在相關(guān)的業(yè)務(wù)庫(kù)中創(chuàng)建 undo_log 表來(lái)存數(shù)據(jù)回滾日志,表結(jié)構(gòu)如下:

--?for?AT?mode?you?must?to?init?this?sql?for?you?business?database.?the?seata?server?not?need?it.
CREATE?TABLE?IF?NOT?EXISTS?`undo_log`
(
????`id`????????????BIGINT(20)???NOT?NULL?AUTO_INCREMENT?COMMENT?'increment?id',
????`branch_id`?????BIGINT(20)???NOT?NULL?COMMENT?'branch?transaction?id',
????`xid`???????????VARCHAR(100)?NOT?NULL?COMMENT?'global?transaction?id',
????`context`???????VARCHAR(128)?NOT?NULL?COMMENT?'undo_log?context,such?as?serialization',
????`rollback_info`?LONGBLOB?????NOT?NULL?COMMENT?'rollback?info',
????`log_status`????INT(11)??????NOT?NULL?COMMENT?'0:normal?status,1:defense?status',
????`log_created`???DATETIME?????NOT?NULL?COMMENT?'create?datetime',
????`log_modified`??DATETIME?????NOT?NULL?COMMENT?'modify?datetime',
????PRIMARY?KEY?(`id`),
????UNIQUE?KEY?`ux_undo_log`?(`xid`,?`branch_id`)
)?ENGINE?=?InnoDB
??AUTO_INCREMENT?=?1
??DEFAULT?CHARSET?=?utf8?COMMENT?='AT?transaction?mode?undo?table';

到這環(huán)境搭建的工作就完事了,完整案例會(huì)在后邊貼出 GitHub 地址,就不在這占用篇幅了。

測(cè)試 Seata

項(xiàng)目中的服務(wù)調(diào)用過(guò)程如下圖:

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
服務(wù)調(diào)用過(guò)程

啟動(dòng)各個(gè)服務(wù)后,我們直接請(qǐng)求下單接口看看效果,只要 order 訂單表創(chuàng)建記錄成功,storage 庫(kù)存表 used 字段數(shù)量遞增、account 余額表 used 字段數(shù)量遞增則表示下單流程成功。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
原始數(shù)據(jù)

請(qǐng)求后正向流程是沒(méi)問(wèn)題的,數(shù)據(jù)和預(yù)想的一樣

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
下單數(shù)據(jù)

而且發(fā)現(xiàn) TM 事務(wù)管理者 order-server 服務(wù)的控制臺(tái)也打印出了兩階段提交的日志

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
控制臺(tái)兩次提交

那么再看看如果其中一個(gè)服務(wù)異常,會(huì)不會(huì)正?;貪L呢?在 account-server 服務(wù)中模擬超時(shí)異常,看能否實(shí)現(xiàn)全局事務(wù)回滾。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
全局事務(wù)回滾

發(fā)現(xiàn)數(shù)據(jù)全沒(méi)執(zhí)行成功,說(shuō)明全局事務(wù)回滾也成功了

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

那看一下 undo_log 回滾記錄表的變化情況,由于 Seata 刪除回滾日志的速度很快,所以要想在表中看見(jiàn)回滾日志,必須要在某一個(gè)服務(wù)上打斷點(diǎn)才看的更明顯。

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))
回滾記錄

總結(jié)

上邊簡(jiǎn)單介紹了 2PC3PC、TCCMQ、Seata 這五種分布式事務(wù)解決方案,還詳細(xì)的實(shí)踐了 Seata 中間件。但不管我們選哪一種方案,在項(xiàng)目中應(yīng)用都要謹(jǐn)慎再謹(jǐn)慎,除特定的數(shù)據(jù)強(qiáng)一致性場(chǎng)景外,能不用盡量就不要用,因?yàn)闊o(wú)論它們性能如何優(yōu)越,一旦項(xiàng)目套上分布式事務(wù),整體效率會(huì)幾倍的下降,在高并發(fā)情況下弊端尤為明顯。

本案例 github 地址:https://github.com/chengxy-nds/Springboot-Notebook/tree/master/springboot-seata-transaction

特別推薦一個(gè)分享架構(gòu)+算法的優(yōu)質(zhì)內(nèi)容,還沒(méi)關(guān)注的小伙伴,可以長(zhǎng)按關(guān)注一下:

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

長(zhǎng)按訂閱更多精彩▼

對(duì)比5種分布式事務(wù)方案,還是寵幸了阿里的Seata(原理 + 實(shí)戰(zhàn))

如有收獲,點(diǎn)個(gè)在看,誠(chéng)摯感謝

免責(zé)聲明:本文內(nèi)容由21ic獲得授權(quán)后發(fā)布,版權(quán)歸原作者所有,本平臺(tái)僅提供信息存儲(chǔ)服務(wù)。文章僅代表作者個(gè)人觀點(diǎn),不代表本平臺(tái)立場(chǎng),如有問(wèn)題,請(qǐng)聯(lián)系我們,謝謝!

本站聲明: 本文章由作者或相關(guān)機(jī)構(gòu)授權(quán)發(fā)布,目的在于傳遞更多信息,并不代表本站贊同其觀點(diǎn),本站亦不保證或承諾內(nèi)容真實(shí)性等。需要轉(zhuǎn)載請(qǐng)聯(lián)系該專欄作者,如若文章內(nèi)容侵犯您的權(quán)益,請(qǐng)及時(shí)聯(lián)系本站刪除。
換一批
延伸閱讀

9月2日消息,不造車的華為或?qū)⒋呱龈蟮莫?dú)角獸公司,隨著阿維塔和賽力斯的入局,華為引望愈發(fā)顯得引人矚目。

關(guān)鍵字: 阿維塔 塞力斯 華為

倫敦2024年8月29日 /美通社/ -- 英國(guó)汽車技術(shù)公司SODA.Auto推出其旗艦產(chǎn)品SODA V,這是全球首款涵蓋汽車工程師從創(chuàng)意到認(rèn)證的所有需求的工具,可用于創(chuàng)建軟件定義汽車。 SODA V工具的開(kāi)發(fā)耗時(shí)1.5...

關(guān)鍵字: 汽車 人工智能 智能驅(qū)動(dòng) BSP

北京2024年8月28日 /美通社/ -- 越來(lái)越多用戶希望企業(yè)業(yè)務(wù)能7×24不間斷運(yùn)行,同時(shí)企業(yè)卻面臨越來(lái)越多業(yè)務(wù)中斷的風(fēng)險(xiǎn),如企業(yè)系統(tǒng)復(fù)雜性的增加,頻繁的功能更新和發(fā)布等。如何確保業(yè)務(wù)連續(xù)性,提升韌性,成...

關(guān)鍵字: 亞馬遜 解密 控制平面 BSP

8月30日消息,據(jù)媒體報(bào)道,騰訊和網(wǎng)易近期正在縮減他們對(duì)日本游戲市場(chǎng)的投資。

關(guān)鍵字: 騰訊 編碼器 CPU

8月28日消息,今天上午,2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)開(kāi)幕式在貴陽(yáng)舉行,華為董事、質(zhì)量流程IT總裁陶景文發(fā)表了演講。

關(guān)鍵字: 華為 12nm EDA 半導(dǎo)體

8月28日消息,在2024中國(guó)國(guó)際大數(shù)據(jù)產(chǎn)業(yè)博覽會(huì)上,華為常務(wù)董事、華為云CEO張平安發(fā)表演講稱,數(shù)字世界的話語(yǔ)權(quán)最終是由生態(tài)的繁榮決定的。

關(guān)鍵字: 華為 12nm 手機(jī) 衛(wèi)星通信

要點(diǎn): 有效應(yīng)對(duì)環(huán)境變化,經(jīng)營(yíng)業(yè)績(jī)穩(wěn)中有升 落實(shí)提質(zhì)增效舉措,毛利潤(rùn)率延續(xù)升勢(shì) 戰(zhàn)略布局成效顯著,戰(zhàn)新業(yè)務(wù)引領(lǐng)增長(zhǎng) 以科技創(chuàng)新為引領(lǐng),提升企業(yè)核心競(jìng)爭(zhēng)力 堅(jiān)持高質(zhì)量發(fā)展策略,塑強(qiáng)核心競(jìng)爭(zhēng)優(yōu)勢(shì)...

關(guān)鍵字: 通信 BSP 電信運(yùn)營(yíng)商 數(shù)字經(jīng)濟(jì)

北京2024年8月27日 /美通社/ -- 8月21日,由中央廣播電視總臺(tái)與中國(guó)電影電視技術(shù)學(xué)會(huì)聯(lián)合牽頭組建的NVI技術(shù)創(chuàng)新聯(lián)盟在BIRTV2024超高清全產(chǎn)業(yè)鏈發(fā)展研討會(huì)上宣布正式成立。 活動(dòng)現(xiàn)場(chǎng) NVI技術(shù)創(chuàng)新聯(lián)...

關(guān)鍵字: VI 傳輸協(xié)議 音頻 BSP

北京2024年8月27日 /美通社/ -- 在8月23日舉辦的2024年長(zhǎng)三角生態(tài)綠色一體化發(fā)展示范區(qū)聯(lián)合招商會(huì)上,軟通動(dòng)力信息技術(shù)(集團(tuán))股份有限公司(以下簡(jiǎn)稱"軟通動(dòng)力")與長(zhǎng)三角投資(上海)有限...

關(guān)鍵字: BSP 信息技術(shù)
關(guān)閉
關(guān)閉