前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >用过XA分布式事务吗?

用过XA分布式事务吗?

作者头像
普通程序员
发布2019-11-20 22:26:13
1.2K0
发布2019-11-20 22:26:13
举报
文章被收录于专栏:普通程序员

一、DTP模型

下图说明了一个DTP系统的本地实例,其中AP调用TM来构造事务。这些框表示X/Open DTP模型中的软件组件。箭头指示控制流的方向。

图中(3)标识的接口就是XA接口,即TM和RMs相互作用的接口(双向接口)。XA接口不是一个普通的应用程序编程接口(API)。它是DTP软件组件之间的系统级接口。X/Open正在开发其他DTP接口,供应用程序直接使用。

XA是由X/Open组织提出的分布式事务的规范。X/Open是一个独立的、全球性的开放系统组织,由世界上最大的信息系统供应商、用户组织和软件公司提供支持。它的使命是通过开放系统的实际实现,从计算中为用户带来更大的价值。

X/Open DTP(Distributed Transaction Process)是一个分布式事务模型。这个模型主要使用了两段提交(2PC - Two-Phase-Commit)来保证分布式事务的完整性。在这个模型里面,有三个角色

AP(An application Program),应用程序。也就是业务层,定义事务边界并指定构成事务的操作。直白一点,哪些操作属于一个事务,就是AP定义的。

RM(Resource Manager),资源管理器。一般是数据库,也可以是其他的资源管理器,如消息队列(如JMS数据源),文件系统等。提供对共享资源的访问。

TM(Transaction Manager),事务管理器。接收AP的事务请求,对全局事务进行管理,管理事务分支状态,协调RM的处理,通知RM哪些操作属于哪些全局事务以及事务分支等等。这个也是整个事务调度模型的核心部分。

文章开头的图只是一个最简单的模型,用于说明原理。实际系统往往会由多个简单的模型组合起来形成一个TM域。下图的域包括2个简单模型。

图中红框的角色

CRM(Communication Resource Manager),CRM允许模型的一个实例访问当前TM域内部或外部的另一个实例。

二、两阶段提交

所有关于分布式事务的介绍中都必然会讲到两阶段提交,它是实现XA分布式事务的关键(确切地说:两阶段提交主要保证了分布式事务的原子性,即所有结点要么全做要么全不做)。两个阶段是指准备阶段和提交阶段。

一个描述两阶段提交很好的类比是典型的结婚仪式,每个参与者(结婚典礼中的新郎和新娘)都必须服从安排,在正式步入婚姻生活之前说“我愿意”。存在一种悲剧情形,“参与者”之一在做出承诺前的最后一刻反悔。两阶段提交也类似,如果有一个参与者不确认成功,整个事务就失败了。

当客户端向事务管理器(TM)发出commit()请求,事务管理器开始两阶段提交过程。在第一阶段,所有的资源被轮询到,问它们是否准备好了提交作业。每个参与者可能回答“准备好(READY)”,“只读(READ_ONLY)”,或“未准备好(NOT_READY)”。如果有任意一个参与者在第一阶段响应“未准备好(NOT_READY)”,则整个事务回滚。如果所有参与者都回答“准备好(READY)”,那这些资源就在第二阶段提交。回答“只读(READ_ONLY)”的资源,则在协议的第二阶段处理中被排除掉。

下图展示了两阶段提交的基本流程

三、一般编程方式

1、配置TM,通过TM或者RM提供的方式,把RM注册到TM。可以理解为给TM注册RM作为数据源。一个TM可以注册多个RM。

2、AP从TM获取资源管理器的代理(例如:使用JTA接口,从TM管理的上下文中,获取出这个TM所管理的RM的JDBC连接或JMS连接)

3、AP向TM发起一个全局事务。这时,TM会通知各个RM。XID(全局事务ID)会通知到各个RM。

4、AP通过2中获取的连接,直接操作RM进行业务操作。这时,AP在每次操作时把XID(包括所属分支的信息)传递给RM,RM正是通过这个XID与3步中的XID关联来知道操作和事务的关系的。

5、AP结束全局事务。此时TM会通知RM全局事务结束。

6、开始二段提交,也就是prepare - commit的过程。

上边几点更多停留在方法论的层面,我基于springboot做了个实验

1、引入jta+atomikos依赖。jta是java对XA接口的实现,atomikos是一个事务管理器(atomikos也是最早做商用分布式事务产品的公司)

2、配置多数据源。一个是本地安装的mysql,另一个采用公司的测试数据库

3、编写数据源配置代码

4、剩下的工作就跟springboot的写本地事务完全一样,用好@Transactional标签就好。spring会帮你搞定剩下的一切功能!

很简单就搞定了不同数据库之间的事务问题。分布式事务是不是就是这么简单呢?显然不是

四、XA的局限性

目前,Oracle、Informix、DB2和Sybase等各大数据库厂家都提供对XA的支持,很幸运,MySQL 5.0以后的版本也支持。是不是可以放心使用MySQL的XA功能呢?我咨询了公司的DBA。

DBA给我推荐了一篇他整理的文章

http://48fc26d1.wiz03.com/wapp/pages/view/share/s/18_2rh2TVh7v2YT4pP1INFGM1B-ldX2v2Ajd2-5SPz0niqbR

文章里提到了MySQL的XA功能存在的问题

1、阻塞问题

两阶段提交执行过程中,所有的参与者都需要听从协调者的统一调度,期间处于阻塞状态而不能从事其他操作,这样效率及其低下。

2、单点故障

由于协调者的重要性,一旦协调者C发生故障。参与者si会一直阻塞下去。尤其在第二阶段,协调者发生故障,那么所有的参与者还都处于锁定事务资源的状态中,而无法继续完成事务操作。(如果是协调者挂掉,可以重新选举一个协调者,但是无法解决因为协调者宕机导致的参与者处于阻塞状态的问题),二阶段提交的缺陷在于如果C崩溃,所有Si可能都需要等待C,从而产生阻塞。

3、数据不一致

在二阶段提交的阶段二中,当协调者向参与者发送commit请求之后,发生了局部网络异常或者在发送commit请求过程中协调者发生了故障,这会导致只有一部分参与者接受到了commit请求。而在这部分参与者接到commit请求之后就会执行commit操作。但是其他部分未接到commit请求的机器则无法执行事务提交。于是整个分布式系统便出现了数据不一致性的现象。--解决方式是

set global tx_isolation='serializable',session tx_isolation='serializable';

此外文章还详细记录了MySQL 外部XA崩溃恢复的过程,一些Demo代码以及更细节的原理分析等,推荐阅读。

除了以上3点,现在系统都采用分布式架构,一个分布式事务很多时候不是亲自去操作另一个数据库,而是去调用其他团队的服务。其他团队的服务很可能不支持XA协议!

最后,支持XA协议的不只是数据库,看看下图的Message Broker

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2019-11-14,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 普通程序员 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
云数据库 SQL Server
腾讯云数据库 SQL Server (TencentDB for SQL Server)是业界最常用的商用数据库之一,对基于 Windows 架构的应用程序具有完美的支持。TencentDB for SQL Server 拥有微软正版授权,可持续为用户提供最新的功能,避免未授权使用软件的风险。具有即开即用、稳定可靠、安全运行、弹性扩缩等特点。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档