javascript
Spring Cloud Alibaba —— Seata 分布式事务框架
導航
- 一、Seata 介紹
- 二、Seata 的工作原理
- 2.1 三個角色
- 2.2 工作流程
- 三、Seata AT 工作機制
- 3.1 一階段
- 3.2 二階段
- 四、案例演示(待補充)
一、Seata 介紹
官網:Seata 官網
Seata 是2019 年阿里巴巴中間件團隊發(fā)起的開源項目,其前身是 Fescar(Fast & EaSy Commit And Rollback)。其愿景是讓分布式的使用像本地事務的使用一樣簡單、高效,并逐步解決開發(fā)者遇到的分布式事務方面的所有難題。
Seata 意為 Simple Extensible Autonomous Transaction Architecture,簡單可擴展自治分布式框架。
Seata 的設計目標是對業(yè)務無侵入,因此從業(yè)務無侵入的 2PC 方案入手,在傳統(tǒng) 2PC 的基礎上擴展,把一個分布式事務理解成一個包含若干分支事務的全局事務
二、Seata 的工作原理
2.1 三個角色
1、TC:Transaction Coordinator 事務協(xié)調器,管理全局的分支事務狀態(tài),用于全局性事務的提交和回滾。
2、TM:Transaction Manager 事務管理器,用于開啟、提交或回滾全局事務。
3、RM:Resource Manager 資源管理器,用于分支事務上的資源管理,向 TC 注冊分支事務,上報分支事務的狀態(tài),接收 TC 的命令來提交或回滾分支事務。
2.2 工作流程
假設上圖中的三個服務根據(jù)調用關系為 A–> B–>C,那么 Seata 的執(zhí)行流程如下:
1、A 服務的TM 向TC申請開啟一個全局事務,TC會創(chuàng)建一個全局事務并返回一個 唯一的 XID。
2、A 服務的 RM向 TC注冊分支事務,并將其納入 XID 對應全局事務的管轄。
3、A 服務執(zhí)行分支事務,操作數(shù)據(jù)庫。
4、A 服務開始遠程調用 B 服務,此時XID 會在微服務的調用鏈上傳播。
5、B 服務的 RM 向TC 注冊分支事務,并將其納入 XID 對應的全局事務的管轄。
6、B 服務執(zhí)行分支事務,操作數(shù)據(jù)庫。
7、全局事務調用鏈處理完畢,TM 根據(jù)有無異常向 TC 發(fā)起全局事務的提交或回滾。
8、TC 協(xié)調其管轄下的所有分支事務,決定是否回滾。
Seata 實現(xiàn) 2PC 與傳統(tǒng) 2PC 的區(qū)別:
1、架構層次方面,傳統(tǒng) 2PC 方案的 RM 實際上是在數(shù)據(jù)庫層,RM 本質就是數(shù)據(jù)庫,通過 XA 協(xié)議實現(xiàn),而 Seata 的 RM 是以 jar 包的形式作為中間件層部署在應用程序這一側的。
2、兩階段提交方面,傳統(tǒng) 2PC 無論第二階段的決議是 commit 還是 rollback ,事務性資源的鎖都要保持到 Phase 2 完成才釋放。而 Seata 的做法是在 Phase 1 就將本地事務提交,這樣就可以省去 Phase 2 持鎖的時間,整體提高效率。
三、Seata AT 工作機制
Seata 在 2PC 提交模型的基礎上進行了演進,視為 Seata AT 模式。除此之外,還有 Seata TCC模式、Seata XA 模式等。
Seata AT 模式非常簡單,也是兩階段提交。
下面以一個簡單示例說明整體 AT 模式的工作機制,參考原文:Seata AT 模式
3.1 一階段
商品表:product :
| id | bigint(20) | PRI |
| name | varchar(100) | |
| since | varchar(100) |
業(yè)務邏輯:
update product set name = 'GTS' where name = 'TXC';1、解析SQL:得到 Sql 類型(update),表(product),條件等信息。
2、查詢前鏡像:根據(jù)解析得到的條件,生成查詢語句,定位數(shù)據(jù):
| 1 | TXC | 2014 |
3、執(zhí)行業(yè)務 SQL:更新這條記錄的 name 為 ‘GTS’。
4、查詢后鏡像:根據(jù)前鏡像的結果,通過 主鍵 定位數(shù)據(jù)。
| 1 | GTS | 2014 |
5、插入回滾日志:把前后鏡像數(shù)據(jù)以及業(yè)務 SQL 相關的信息組成一條回滾日志記錄,插入到 UNDO_LOG 表中。
{"branchId": 641789253,"undoItems": [{"afterImage": {"rows": [{"fields": [{"name": "id","type": 4,"value": 1}, {"name": "name","type": 12,"value": "GTS"}, {"name": "since","type": 12,"value": "2014"}]}],"tableName": "product"},"beforeImage": {"rows": [{"fields": [{"name": "id","type": 4,"value": 1}, {"name": "name","type": 12,"value": "TXC"}, {"name": "since","type": 12,"value": "2014"}]}],"tableName": "product"},"sqlType": "UPDATE"}],"xid": "xid:xxx" }6、提交前,向 TC 注冊分支:申請 product 表中,主鍵值等于 1 的記錄的 全局鎖 。
7、本地事務提交:業(yè)務數(shù)據(jù)的更新和前面步驟中生成的 UNDO LOG 一并提交。
8、將本地事務提交的結果上報給 TC。
3.2 二階段
回滾
1、收到 TC 的分支回滾請求,開啟一個本地事務,執(zhí)行如下操作。
2、通過 XID 和 Branch ID 查找到相應的 UNDO LOG 記錄。
3、數(shù)據(jù)校驗:拿 UNDO LOG 中的后鏡與當前數(shù)據(jù)進行比較,如果有不同,說明數(shù)據(jù)被當前全局事務之外的動作做了修改。這種情況,需要根據(jù)配置策略來做處理,詳細的說明在另外的文檔中介紹。
4、根據(jù) UNDO LOG 中的前鏡像和業(yè)務 SQL 的相關信息生成并執(zhí)行回滾的語句:
5、提交本地事務。并把本地事務的執(zhí)行結果(即分支事務回滾的結果)上報給 TC。
提交
1、收到 TC 的分支提交請求,把請求放入一個異步任務的隊列中,馬上返回提交成功的結果給 TC。
2、異步任務階段的分支提交請求將異步和批量地刪除相應 UNDO LOG 記錄。
四、案例演示(待補充)
演示一個電商下訂單扣庫存的應用案例,看下 Seata 是如何使用的。
總結
以上是生活随笔為你收集整理的Spring Cloud Alibaba —— Seata 分布式事务框架的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: php数组在golang,go语言数据类
- 下一篇: gradle idea java ssm