seata xid是什么_又见分布式事务之阿里开源Seata

Seata是一款由阿里巴巴开源的分布式事务解决方案,它实现了业务层面的无侵入分布式事务处理。Seata通过TM(事务管理器)、TC(事务协调器)和RM(资源管理器)三个组件,使得在微服务架构中操作分布式事务如同本地事务一样简单。Seata使用全局事务和分支事务的概念,每个分支事务是一个满足ACID的本地事务,通过UNDO_LOG表记录回滚数据,实现即使在第一阶段也能直接提交事务。在Seata的AT模式下,它依赖数据库的ACID特性,而MT模式则允许对业务有入侵的自定义操作。
摘要由CSDN通过智能技术生成

欢迎关注头条号:老顾聊技术

精品原创技术分享,知识的组装工

前言

分布式微服务中事务问题,是一直困扰着大家的。之前老顾已经介绍过如何利用rocketmq的事务消息解决事务问题,今天老顾再来介绍另一个方案;提供小伙伴们另一个选择。

解决方案有哪些?

分布式事务方案大致分为对业务无侵入型 和 有侵入型

无侵入型的方案有基于数据库的XA协议的两阶段提交,它的优点对业务无侵入,缺点也很明显;数据库必须支持XA协议,且支持XA协议对性能的影响很大,因为它会造成事务资源长时间得不到释放。数据库的吞吐量极低。

为了解决这个问题,就出来了很多业务层面的实现二阶段的提交方案,如:很出名的 TCC 方案,基于 TCC 也有很多成熟的框架,如 ByteTCC、tcc-transaction。

另一种就是最终一致性的方案,如:rocketmq事务消息。

但上面的TCC方案、或者最终一致性方案都会涉及到业务代码的改造,对业务有侵入

下面我们来介绍一下今天的主角。

Seata

Seata的分布式事务解决方案是业务层面的解决方案,业务层上无需关心分布式事务机制的约束,它将给我们的微服务架构带来质的提升,只依赖于单台数据库的事务能力。

Seata 的设计思路是将一个分布式事务可以理解成一个全局事务,下面挂了若干个分支事务,而一个分支事务是一个满足 ACID 的本地事务,因此我们可以操作分布式事务像操作本地事务一样。

Seata 内部定义了 3个模块来处理全局事务和分支事务的关系和处理过程,这三个组件分别是:

1、Transaction Coordinator (TC): 事务协调器,维护全局事务的运行状态,负责协调并驱动全局事务的提交或回滚。2、Transaction Manager (TM): 控制全局事务的边界,负责开启一个全局事务,并最终发起全局提交或全局回滚的决议。3、Resource Manager (RM): 控制分支事务,负责分支注册、状态汇报,并接收事务协调器的指令,驱动分支(本地)事务的提交和回滚。

其中,TM是一个分布式事务的发起者和终结者,TC负责维护分布式事务的运行状态,而RM则负责本地事务的运行。如下图所示:

cc3bf7f8dfa7e292c25607da65b72ab9.png

下面是一个分布式事务在Seata中的执行流程:

1)TM 向 TC 申请开启一个全局事务,全局事务创建成功并生成一个全局唯一的 XID。2)XID 在微服务调用链路的上下文中传播。3)RM 向 TC 注册分支事务,接着执行这个分支事务并提交(重点:RM在第一阶段就已经执行了本地事务的提交/回滚),最后将执行结果汇报给TC。4)TM 根据 TC 中所有的分支事务的执行情况,发起全局提交或回滚决议。5)TC 调度 XID 下管辖的全部分支事务完成提交或回滚请求。

分支事务为什么能直接提交?

Seata能够在第一阶段直接提交事务,是因为Seata框架为每一个RM维护了一张UNDO_LOG表(这张表需要客户端自行创建),其中保存了每一次本地事务的回滚数据。因此,二阶段的回滚并不依赖于本地数据库事务的回滚,而是RM直接读取这张UNDO_LOG表,并将数据库中的数据更新为UNDO_LOG中存储的历史数据

如果第二阶段是提交命令,那么RM事实上并不会对数据进行提交(因为一阶段已经提交了),而实发起一个异步请求删除UNDO_LOG中关于本事务的记录。

原理就是先保存之前的老数据,一旦出现异常,就是把老数据再更新回去。

Seata执行流程

下面是一个Seata中一个分布式事务执行的详细过程:

1)首先TM 向 TC 申请开启一个全局事务,全局事务创建成功并生成一个全局唯一的 XID

2)XID 在微服务调用链路的上下文中传播

3)RM 开始执行这个分支事务,RM首先解析这条SQL语句,生成对应的UNDO_LOG记录。下面是一条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"}

可以看到,UNDO_LOG表中记录了分支ID,全局事务ID,以及事务执行的redo和undo数据以供二阶段恢复。

4)RM在同一个本地事务中执行业务SQL和UNDO_LOG数据的插入。在提交这个本地事务前,RM会向TC申请关于这条记录的全局锁。如果申请不到,则说明有其他事务也在对这条记录进行操作,因此它会在一段时间内重试,重试失败则回滚本地事务,并向TC汇报本地事务执行失败。如下图所示:

4613f7ee53e81c8cd807bce13a493b3f.png

5)RM在事务提交前,申请到了相关记录的全局锁,因此直接提交本地事务,并向TC汇报本地事务执行成功。此时全局锁并没有释放,全局锁的释放取决于二阶段是提交命令还是回滚命令。

6)TC根据所有的分支事务执行结果,向RM下发提交或回滚命令。

7)RM如果收到TC的提交命令首先立即释放相关记录的全局锁,然后把提交请求放入一个异步任务的队列中,马上返回提交成功的结果给 TC。异步队列中的提交请求真正执行时,只是删除相应UNDO LOG 记录而已。

e0098d32a2c69118454ee3708c434f18.png

8)RM如果收到TC的回滚命令,则会开启一个本地事务,通过 XID 和 Branch ID 查找到相应的 UNDO LOG 记录。将 UNDO LOG 中的后镜与当前数据进行比较:

如果有不同,说明数据被当前全局事务之外的动作做了修改。这种情况,需要根据配置策略来做处理。

否则,根据 UNDO LOG 中的前镜像和业务 SQL 的相关信息生成并执行回滚的语句并执行,然后提交本地事务达到回滚的目的。

最后释放相关记录的全局锁

742f1bc1006cb79390485911a17f1eff.png

方案补充

上面的方案是Seata的默认模式,称为AT模式,它是类似于 XA 方案的两段式提交方案,并且是对业务无侵入,但是这种机制依然是需要依赖数据库本地事务的 ACID 特性。

小伙伴们有没有发现,整个流程的基础必须是支持 ACID 特性的关系型数据库,那么问题就来了,非关系型或者不支持 ACID 的数据库就无法使用 Seata 了?

Seata 现阶段为我们准备了另外一种模式,叫 MT 模式,它是一种对业务有入侵的方案,提交回滚等操作需要我们自行定义,业务逻辑需要被分解为 Prepare/Commit/Rollback 3 部分,形成一个 MT 分支,加入全局事务,其本质就是TCC方案。

不过MT模式,它不是 Seata “主打”的模式,它的存在仅仅作为补充的方案,从以上官方的发展远景就可以看出来,Seata 的目标是始终是对业务无入侵的方案。

总结

今天老顾介绍seata整体原理,以及执行流程,希望小伙伴们能够在原理本质上去先了解一下seata,后面的文章老顾会介绍一下项目实战,谢谢!!!

---End---

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值