系列文章

  1. Seata 源码阅读 (1) - 概述

Seata 是阿里巴巴的开源分布式事务框架,之前叫做 Fescar。它支持“无侵入”地帮助开发者在微服务架构中,保证跨多个机器的操作的事务性。很早以前就听说过这个框架,最近有空来简单看一看它的源代码。这篇文章主要介绍一下在 Seata 中,一个分布式事务的生命周期是怎么样的。

基本组件

Seata 中包含三种基本组件

  1. Transaction Coordinator (TC): 中心化的节点,维护全局事务的状态,决定事务应该被提交还是回滚。
  2. Transaction Manager (TM): 每个业务节点会有一个,用来开始,提交或者回滚一个全局事务。
  3. Resource Manager (RM): 每个业务节点会有一个,管理分支事务,同时会和 TC 报告分支事务的状态,帮助决定全局事务的状态。

下图是一个样例集群的简图。图中有四个微服务,其中 Business 服务是整个业务的入口,当它收到一个请求是,它本地的 TM 会创建一个全局事务,在这个事务中,它会分别调用下游的服务,并把全局事务的 id 发送给它们。

Cluster

上面提到了分支事务和全局事务,这里就不得不引用一下官方图片了。很简单,全局事务是由一个个分支事务构成的。由于是在分布式环境中,每个分支事务就发生在每个不同的节点上。

GlobalAndBranchTransaction

一个分布式事务的生命周期

GlobalTransactionLifeCycle

上图是一个全局事务的主要流程。就像之前对 TM 的描述一样,一个全局事务是由 TM 开启的。TM 会生成一个 XID,并发送给 TC。在接下来的所有操作中,XID 会被发送给依赖服务。

对于每一个微服务,它们的 RM 收到 XID 之后就意识到自己在参与一个全局事务中。它会在这个全局事务下,向 TC 注册自己的本地事务,并报告自己本地事务的状态。

TC 作为 Coordinator,会根据一个 XID 下的所有本地事务的状态,来决定这个全局事务是否需要提交。这个决定会发送给 TM 和 RM。

本地事务

LifeCycle

对于一个本地事务来说,RM 除了提交本地事务之外,会根据事务前后的状态,生成 undo log。这样即使本地事务提交之后,TC 还是决定要回滚(比如其他分支事务提交失败),就可以根据 undo log 来恢复。

隔离性

看到这里,我相信你一定在考虑,这样的话,不是会读到没有被“提交”的数据么?确实,Seata 默认的隔离级别是 Read Uncommitted。但是它说自己可以支持 Read Committed,我还没看到是怎么实现的,之后再更新吧。