分布式事务方案对比

先明确一个核心前提

分布式事务要解决的是:一个业务操作跨了多个数据库或服务,如何保证数据一致性?

解决方案分为两大阵营:

  • 刚性事务(强一致性):Seata 的 AT、TCC、XA 模式。追求数据实时一致,所有服务要么一起成功,要么一起失败。

  • 柔性事务(最终一致性):本地消息表、MQ 事务消息。允许短暂不一致,通过重试保证数据最终一定对齐。

本地消息表

核心思想 :在本地业务数据库里建一张 outbox 表,把"写业务数据"和"写待发送消息"放在同一个本地事务里。业务成功后,用一个定时任务去扫 outbox 表,把消息发给 MQ,发送成功后再删除或标记这条消息。

特点

  • 优点:实现简单,不依赖特殊 MQ,和业务代码耦合低。

  • 缺点:需要自己写定时任务和异常处理;消息可能重复发送,消费者必须幂等;有延迟,定时任务扫描间隔决定了消息的延迟时间。

适用场景:公司没有 RocketMQ 这类支持事务消息的 MQ,只能用 RabbitMQ 或 Kafka,但又需要保证消息一定发出去。

MQ 事务消息

核心思想:利用 RocketMQ 原生的事务消息机制,把"发送消息"和"执行本地事务"绑定在一起。先发半消息(消费者不可见),再执行本地事务,根据本地事务结果决定半消息是提交(消费者可见)还是回滚(丢弃)。

特点

  • 优点:消息延迟低(实时性远高于本地消息表),不需要自己写定时任务和 outbox 表,RocketMQ 自带回查机制保证最终一致性。

  • 缺点:必须用 RocketMQ(RabbitMQ 和 Kafka 原生不支持);消费者必须幂等。

适用场景:公司有 RocketMQ,且对数据一致性的实时性要求高------比如下单后要立刻扣库存,不能等几秒后才发消息。

Seata AT 模式

核心思想:Seata 介入你的 SQL 执行过程,在事务提交前自动记录回滚日志(undo_log 表)。如果需要回滚,Seata 根据 undo_log 自动生成反向 SQL,把数据恢复原状。你的代码不需要写任何回滚逻辑。

特点

  • 优点 :对业务代码零侵入(只需一个 @GlobalTransactional 注解),自动生成回滚日志,自动回滚。

  • 缺点 :依赖 Seata Server(需要额外部署);性能损耗比本地事务高;不支持 Redis、MongoDB 等非关系型数据库;不支持 SELECT ... FOR UPDATE 这类显式加锁的 SQL。

适用场景:Java 微服务项目,数据库全部是 MySQL(或其他关系型数据库),不想侵入业务代码,想用注解自动管理分布式事务。

Seata TCC 模式

核心思想:TCC 把每个服务需要做的事情拆成三步:Try(锁定资源)、Confirm(正式执行)、Cancel(释放资源)。所有 Try 都成功后,统一 Confirm;任何一个 Try 失败,统一 Cancel。这是业务层面的补偿,不是数据库层面的回滚。

特点

  • 优点:性能更高(没有全局行锁),支持非数据库资源(Redis、文件系统等),业务可控性强。

  • 缺点:代码侵入性极高,每个接口都需要实现 Try、Confirm、Cancel 三个方法;开发工作量大,容易出错。

适用场景:对性能要求极高的场景(比如秒杀扣库存),或者涉及非数据库资源(需要同时操作 Redis 和 MySQL),或者公司已经有 TCC 框架沉淀。

Seata XA 模式

核心思想:利用数据库自身的 XA 协议(两阶段提交)。Seata 不在 SQL 层面做拦截,而是把分布式事务完全交给数据库去管理。第一阶段各数据库执行 SQL 但不提交(Prepare),第二阶段 Seata 通知所有数据库统一提交或回滚(Commit/Rollback)。

特点

  • 优点:对业务代码几乎零侵入;强一致性,数据绝不脏读。

  • 缺点:性能最差(全局锁持有时间长,并发吞吐量断崖式下降);依赖数据库支持 XA 协议(MySQL 5.7+ 支持);不支持 Redis 等非数据库资源。

适用场景:对数据一致性要求极高(比如金融、会计系统),但对性能要求不高,且所有资源都是支持 XA 协议的关系型数据库。在实际生产中很少使用,因为性能代价太大。

Seata Saga 模式

核心思想是把一个长事务拆成多个短事务,每个短事务都有自己的补偿操作。如果某个步骤失败,不再回滚已经成功的步骤,而是按顺序反向执行补偿操作。

优点 是不依赖全局锁和 undo_log,适合长事务(如需要人工审核的订单流程);缺点是必须为每个正向操作编写反向补偿逻辑。

这种方式适用场景是业务流程长、需要人工干预或调用外部系统(如银行接口)。

总结

没有银弹。刚性事务(AT、TCC、XA)追求强一致性,但各有代价;柔性事务(本地消息表、MQ 事务消息)允许短暂不一致,但通过重试保证最终对齐。架构设计的本质是权衡------你在选择方案的同时,也是在选择你愿意为数据一致性付出多大的性能代价。

相关推荐
向夏威夷 梦断明暄1 天前
从架构特点到功能缺陷,重新认识分析型分布式数据库
数据库·分布式·架构
AAA@峥1 天前
Ceph 集群配置管理完整指南
运维·数据库·分布式·ceph
心如鉄补1 天前
分布式链路追踪系统之docker-compose安装skywalking
分布式·docker·skywalking
努力努力再努力wz1 天前
【分布式系统与 RPC 框架系列】从单机瓶颈到远程调用:一文理解分布式架构与 RPC 原理
linux·网络·c++·分布式·网络协议·rpc·架构
ACP广源盛139246256731 天前
此芯 P1 AI BOX / AI NAS@ACP#IX8008、IX8024 应用场景与市场机会
大数据·人工智能·分布式·单片机·嵌入式硬件
网络工程小王2 天前
【HCIE-AI】12.deepspeed分布式并行训练进阶版
人工智能·pytorch·分布式·学习·昇腾·deepspeed
ACP广源盛139246256732 天前
国产算力互联IX8024@ACP#Kimi K3 开源后的端侧部署硬件架构分析
大数据·人工智能·分布式·单片机·嵌入式硬件
花生了什么事o2 天前
分布式 ID 生成方案:从数据库自增到雪花算法
数据库·分布式·算法
爱吃提升3 天前
python 分布式爬虫、爬虫合规与综合实战项目
分布式·爬虫·python