文章23 | 阅读 16358 | 点赞0
本文基于seata 1.3.0版本
在AT模式下,服务端集群部署很简单,如果集群是在一台机器上,复制一份程序,修改一下端口号,启动即可。
因为集群部署很简单,本文不再对部署做介绍,本文向介绍一下TM、RM如何与集群建立连接,以及集群中各机器如何通讯。
RM启动的时候要向TC注册,根据事务分组从注册中心找到该分组对应的服务集群,之后与集群中的每台机器建立连接,并向每台机器注册RM。
与集群建立连接是在NettyClientChannelManager的reconnect方法中完成的,代码如下:
//该方法的入参是事务分组
void reconnect(String transactionServiceGroup) {
List<String> availList = null;
try {
//从注册中心获得与事务分组对应的集群中每台机器地址
//transactionServiceGroup是事务分组,通过配置spring.cloud.alibaba.seat.tx-service-group指定
availList = getAvailServerList(transactionServiceGroup);
} catch (Exception e) {
LOGGER.error("Failed to get available servers: {}", e.getMessage(), e);
return;
}
//如果集群中没有机器提供服务,那么打印出日志,seata启动定时任务线程每过一段时间会重新查看集群中是否有机器
if (CollectionUtils.isEmpty(availList)) {
String serviceGroup = RegistryFactory.getInstance()
.getServiceGroup(transactionServiceGroup);
LOGGER.error("no available service '{}' found, please make sure registry config correct", serviceGroup);
return;
}
//遍历每台机器
for (String serverAddress : availList) {
try {
//建立与TC的连接,并注册RM
acquireChannel(serverAddress);
} catch (Exception e) {
LOGGER.error("{} can not connect to {} cause:{}",FrameworkErrorCode.NetConnect.getErrCode(), serverAddress, e.getMessage(), e);
}
}
}
注意RM是与集群中的每台机器都建立连接,那么之后RM与TC通讯时,比如注册分支事务,RM是与集群中的一条机器通讯还是与所有的机器通讯?
答案是一台机器。
RM与TC通讯时,首先也是根据事务分组从注册中心找到集群机器列表,之后使用负载均衡策略,从列表中选出一台机器,因为已经与每台TC建立了连接,所以这里不用再建立连接而是直接使用。seata提供了两种负载均衡策略:随机和轮询。可以参见的代码AbstractNettyRemotingClient的sendSyncRequest方法。
TM与集群通讯和RM基本是一致。
TM启动时,也是根据事务分组从注册中心找到集群机器列表,然后与每台机器建立连接,并向其注册TM信息。
启动后的通讯也是根据负载均衡策略与其中一台机器通讯。而且对于同一个全局事务,可能TM访问的机器前后是不同的。TM和RM与集群通讯使用的代码都是一样的。
RM、TM在启动后都是与集群中一台机器通讯,而且就同一个全局事务前后交互的机器可能不同,那么事务数据如何在集群中共享?另外为什么RM或者TM注册必须向每台机器注册,而之后的交互则不用?
先来看第一个问题。服务端收到TM或者RM的请求后,如果是事务注册请求,则会将注册的事务数据写入文件、redis或者数据库,具体写入哪个可以使用store.mode配置。之后事务的提交、回滚或者查询都是根据事务XID从文件、redis或者数据库查询出事务数据,然后更新的。所以如果服务端集群部署,事务数据存储必须使用redis或者数据库。
第二个问题,为什么必须向每台机器都注册。因为注册信息是记录在内存中的,不写入数据库,而且各个机器之间也没有通过网络交换注册信息,注册信息记录在ChannelManager的IDENTIFIED_CHANNELS属性中。
下面先详细介绍一下RM如何查找TC机器列表,这也是上面代码中方法getAvailServerList的执行过程。
通过上述流程可以看到,事务分组是一个与集群相关的概念,可以将若干个RM、TM、TC形成一个逻辑分组,相当于一个资源单位,可以做资源隔离。
事务分组并不是直接映射到TC列表,而是中间经过service.vgroupMapping配置中转,这样做的好处是,service.vgroupMapping配置可以放到配置中心,一旦TC集群发生故障,通过修改配置中心值,在不停机的情况下切换到另一个TC集群。
版权说明 : 本文为转载文章, 版权归原作者所有 版权申明
原文链接 : https://blog.csdn.net/weixin_38308374/article/details/108944877
内容来源于网络,如有侵权,请联系作者删除!