Java教程

百万架构师核心技术设计实践——分布式事务设计

本文主要是介绍百万架构师核心技术设计实践——分布式事务设计,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!

一、出现分布式事务的原因:

  • 只跨库:单体的读写分离。注:库不仅仅指的db,还有cache
  • 只跨服务:服务拆分库未拆分,由于不同服务开启不同的的数据库链接
  • 跨库跨服务:即跨库又跨服务

二、分布式事务分类:

刚性分布式事务:强一致性(cp)

  • xa、2pc、3pc

柔性分布式事务(使用多):最终一致性(ap,补偿/通知)

  • 补偿性事务:TCC、saga。通过补偿性方法,使得数据恢复,属于同步事务
  • 通知性事务:事务消息、最大努力通知事务。通过第三方(MQ)通知事务下游,属于异步事务

三、六大事务模型:

刚性事务模型:xa,2pc(两阶段提交又称2PC(two-phase commit protocol))
柔性事务模型:补偿类2(TCC、saga),通知类2(事务消息、最大努力通知事务)
注:saga与事务通知重点介绍

四、刚性分布式事务:

提到刚性分布式事务,首先想到的是2pc,在2pc之前首先应了解XA模型,刚性事务满足传统事务的ACID(ACID介绍: 传送门)
柔性事务对ACID的CI进行了取舍,刚性分布式事务由于性能差,在实际应用中使用很少,除非是对事务要求极为苛刻的金融公司,如蚂蚁金服大量使用2pc

五、XA模型(只是标准,无具体实现):

XA模型仅仅是定义了规范,使用的时候需要各个厂自己实现。目前XA具有很大性能问题,几乎没人用。 且只能用XA事务连接池,不能用jdbc
1.XA由AP、RM、TM组成:
在这里插入图片描述

六、2PC(XA模型的实现 two-phase commit protocol):

基于xa模式的2pc实现时序图:
在这里插入图片描述
两阶段提交2PC是XA模型的实现,AP发起commit请求,TM发起prepare投票,RM进行串行投票,都同意后,TM再commit,如果commit过程出现宕机等异常,节点服务重启后,根据XA recover再次进行commit补偿。

缺点(响应延时高、并发低):

  • 同步阻塞模型
  • 数据库资源锁锁定时间过程
  • 全局锁(隔离级别串行化),并发低
  • 不适合长事务场景,长事务(即事务多)

七、3PC(there-phase commit protocol):

  • 为进行改进2pc,3pc1981提出,1982年确认理论方法,2pc是1978年提出,距今已经近50。

3pc是2pc的优化,不是严格的XA规范,解决脑裂引起的事务状态不确定问题,引入了超时和对齐(根据上次的结果,默认执行)的概念。如TM约定,5秒后提交事务,等待5秒,然后提交事务,如果存在未收到状态的RM,默认对齐。sql层面是,01解析sql,02记undo/redo,03提交事务。3pc比2pc多引入一个阶段,仅仅解决的是2pc因脑裂带来的事务状态丢失的问题(这是小缺陷),对于2pc的大缺陷(同步、并发低)一个也没解决,2pc还有很少的人用,3pc几乎根本没人用。

八、柔性分布式事务:

刚性分布式事务由于性能差(高延时、低吞吐量),在实际应用中使用很少,除非是对事务要求极为苛刻的金融公司,如蚂蚁金服大量使用2pc,在互联网高并发的要求下,2pc这类的刚性分布式事务根本无法满足我们的需求,因此出现的如TCC、saga类的柔性分布式事务。刚性事务在业内估计占有10%-20%
柔性分布式事务是对XA的妥协,降低对一致性的要求,从而降低数据库资源(RM)的锁定时间,提高性能。cap选取ap柔性分布式事务,而柔性分布式事务的落地理论就是base理论。base理论传送门

九、TCC(try-confirm-cancel)模型:

理论神器、初学者天堂、实践废物,对业务侵入性很大。TCC07年提出,09年引入国内
在这里插入图片描述

  • try:尝试执行业务、完成所有业务检查,预留必要的业务资源(冻结)
  • confirm:真正的执行业务,不再做业务检查
  • cancel:释放try阶段预留的资源
    看着和xa的2pc一样,实际上不同2pc是数据库层面的,tcc的业务层面,对业务侵入性强
    举例:A用户向B用户转账500块
    在这里插入图片描述可以看出存在中间柔性状态,最终达到一致性,对数据的一致性做了取舍,而且通过中间字段对数据隔离性做了取舍。满足base理论。
    但操作一步变3步,字段一个变3个,使得业务变复杂,而且应用的场景很有限,很难落地。
    tcc的问题:
  • 问题1:网络丢失,如果子服务A执行完,子服务B的TryY出现网络抖动,网络丢失,一段时间后服务A超时,子服务B将空回滚可借鉴XA引入TM(记录xid、事务状态等信息)
  • 问题2:网络超时,如果子服务A执行完,子服务B的TryY出现网络超时,一段时间后服务A超时,子服务B将空回滚,然后B的TryY执行成功,会造成资源悬挂问题。所以姗姗来迟的请求要拒绝,防悬挂可借鉴XA引入TM(记录xid、事务状态等信息)
  • 问题3:服务幂等,如果服务重试可能执行多次要做服务幂等,服务幂等是分布式系统的必备要求。

在这里插入图片描述
在这里插入图片描述

九、saga模型:

  • 起源于1987年的论文《Sagas》
  • saga模型把分布式事务拆分成多个本地事务,每个本地事务都有相应的执行模块与补偿模块。
  • 当saga事务中某个本地事务出错时,可通过调用相关的补偿方法恢复之前的事务(当第n个本地事务出错,补偿前n-1本地事务,因为第n个自己会回滚),达到最终一致性。
    在这里插入图片描述

tcc是三步,首先try如果失败就回滚;saga是两步,直接execute,正常就结束了,异常就调用补偿模块,补偿模块可能复用(巨大的优化);saga也是串行化的?saga的串行与xa模式的串行不一样,saga的每个本地事务执行后都会提交,xa模式每个本地事务执行后不会提交,而是挂起。

saga的隔离性:

  • 业务层控制并发(分布式锁)
  • 应用层加锁(分布式锁)
  • 应用层预先冷冻资源(业务隔离(业务中间态),如转账a转b,不直接转,而是转给中间账户,成功的话中间账户再转给b,在金融行业中间账号很常见)

saga的补偿模块:

  • 向后恢复:补偿所有与完成的事务,如果任何一个事务失败。(历史回溯,Aop实现)
  • 向前恢复:重试失败的事务,直到每个子事务最终都会成功。(异步,预先配置好流程,工作流状态机实现)

saga的问题:

  • 问题1:空补偿可借鉴XA引入TM(记录xid、事务状态等信息)
  • 问题2:服务幂等

tcc与saga的cancal与补偿可以异步,fastfail,三次补偿失败就上人工智能(人)

十、刚性分布式事务与柔性分布式事务比较:

在这里插入图片描述

十一、遇到分布式事务的解决思路与方案:

  • 业务规避->控制成本
  • 能否异步->事务消息(半消息)
  • 能否柔性->saga
  • 2pc
  • tcc->业务一致性

十二、事务消息:

事务消息是柔性分布式事务,通知型
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

缺点:

  • mq需要支持半消息与消费保证,mq还可能存在时序性问题
  • 业务需要改造,可进行事务回查
  • 消费端需要处理幂等问题

优化:引入本地事务消息表,可解决发送端的原子性问题。将消息插入本地表,定时任务投递mq

在这里插入图片描述

十三、同步场景实现分布式事务设计:

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
补偿方法不一定写,curd,c与d对立,直接由,只需要写u操作,且bas为数据处理层,不涉及业务,可以写通用的(如果标注了补偿方法,就走个性的补偿方法,没有标注的就走通用的补偿方法)

十四、更优雅的补偿方案——seata-AT模式:

seata-AT模式也是saga的一种实现:自动补偿:
写操作前,生成前置镜像
写操作
写操作前,生成后置镜像;如果补偿,对比前后镜像,进行补偿

十五、saga开源方案:

tcc也有开源方案,但是实现成本太大,不推荐使用,如seata tcc模式,bytetcc
在这里插入图片描述service comb是华为的一套微服务解决方案,不是独立的模块,如果使用需要使用全套的微服务解决方案。使用的是saga aop实现

seata是阿里的产品,支持AT、saga、tcc、xa模式,语言上支持java支持go;而且支持全局锁,解决事务隔离的问题

  • AT->saga Aop
  • TCC->TCC
  • Saga->saga 状态机
  • XA->2PC

seata的清铭(肖宇)为了制定标准,给saga对着干

在这里插入图片描述

Hmily是个人产品

这篇关于百万架构师核心技术设计实践——分布式事务设计的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!