Saga 分布式事务模式详解

先喝口水,再看一眼分布式系统,然后你会发现:没有事务,心里没底;有了事务,系统要命。

作为一名写了很多年 Java 的老兵,今天我们来聊一个在微服务世界里既不完美、但很实用 的方案------Saga 分布式事务模式。


一、为什么需要 Saga?(问题从哪来)

在单体应用里,事务是这样的:

text 复制代码
BEGIN
  A 表扣钱
  B 表加库存
  C 表创建订单
COMMIT / ROLLBACK

一切都很美,直到:

  • 服务被拆成了 微服务
  • 数据库被拆成了 多个库
  • 本地事务失效了

你会发现:

分布式系统里,没有一个"全局数据库事务"在等你。

传统方案的问题

  • 2PC / XA:

    • 强一致
    • 强依赖
    • 强性能杀手

于是我们开始思考:

能不能不要强一致,但系统还能跑?

答案就是:Saga。


二、Saga 是什么?(一句话版本)

Saga = 一连串本地事务 + 对应的补偿事务

换句话说:

  • 每一步都 先提交
  • 如果后面失败了
  • 就 按相反顺序补偿回去

听起来是不是有点像:

"做错了事,靠后悔药解决。"

没错,但这药在分布式系统里,很值钱。


三、Saga 的核心思想(重要但不复杂)

1️⃣ 本地事务优先

每个服务:

  • 只操作 自己的数据库
  • 使用 本地事务(Spring @Transactional 那套)

2️⃣ 失败 ≠ 回滚

Saga 的世界里:

  • 失败不是 rollback
  • 而是:

执行补偿操作(Compensation Action)

3️⃣ 最终一致性

  • 中间状态可能不一致
  • 但最终能"对上账"

一句话总结:

Saga 不保证你时时开心,但保证你最后不崩。


四、Saga 的两种经典实现方式

方式一:编排式 Saga(Orchestration)⭐ 推荐

有一个指挥官,统一调度流程。

sequenceDiagram participant SagaCoordinator participant OrderService participant PaymentService participant InventoryService SagaCoordinator->>OrderService: 创建订单 SagaCoordinator->>PaymentService: 扣款 SagaCoordinator->>InventoryService: 扣库存 InventoryService-->>SagaCoordinator: 失败 SagaCoordinator->>PaymentService: 退款(补偿) SagaCoordinator->>OrderService: 取消订单(补偿)

优点:

  • 流程清晰
  • 易于监控
  • 逻辑集中

缺点:

  • 指挥官可能变胖

但对 Java 后端来说,这个"胖"是可以接受的。


方式二:编舞式 Saga(Choreography)

没有指挥官,全靠服务自己"看消息办事"。

graph LR Order -->|事件| Payment Payment -->|事件| Inventory Inventory -->|失败事件| Payment Payment -->|补偿事件| Order

优点:

  • 去中心化

缺点:

  • 链路难追踪
  • Debug 靠信仰

一旦系统大了,没人知道谁在跳哪支舞。


五、一个下单场景的 Saga 示例(Java 思路)

正向流程

  1. 创建订单(Order Service)
  2. 扣减余额(Payment Service)
  3. 扣减库存(Inventory Service)

补偿流程

  • 库存失败 → 退款 → 取消订单

伪代码示例(编排式)

java 复制代码
public void createOrderSaga(CreateOrderCmd cmd) {
    try {
        orderService.create(cmd);
        paymentService.pay(cmd);
        inventoryService.deduct(cmd);
    } catch (Exception e) {
        inventoryService.compensate(cmd);
        paymentService.refund(cmd);
        orderService.cancel(cmd);
        throw e;
    }
}

看起来很普通,对吧?

但它解决的是分布式事务这个"世纪难题"。


六、Saga 的几个关键设计点(血泪经验)

1️⃣ 补偿必须是幂等的

  • 可能被调用多次
  • 不能多退钱、多加库存

幂等不是优化,是底线。


2️⃣ 补偿 ≠ 完全回滚

  • 有些操作不可逆(比如发短信)
  • 补偿只能"业务上对等"

分布式系统里, 时间不能倒流,只能对冲。


3️⃣ 一定要有状态表

  • Saga 实例状态
  • 当前执行到哪一步
  • 是否已补偿

否则:

系统一重启,你会失忆。


七、Saga vs 2PC(快速对比)

维度 Saga 2PC
一致性 最终一致 强一致
性能 高 低
实现复杂度 中 高
可用性 高 低
微服务友好度 ⭐⭐⭐⭐⭐ ⭐

结论一句话:

微服务时代,用 Saga;银行核心,用 2PC。


八、Java 技术栈中的 Saga 实践

常见组合:

  • Spring Boot
  • Spring Transaction
  • 消息队列(Kafka / RocketMQ)
  • 状态表 + 定时补偿

进阶框架:

  • Axon
  • Eventuate Tram
  • 自研 Saga Coordinator(很多公司最终都会走这条路)
相关推荐
行者全栈架构师3 小时前
【鸿蒙心迹】让老照片变清晰:HarmonyOS 7.0 图像超分相册工程化落地与 5 个踩坑解法
架构·前端框架·开源
再__努力1点3 小时前
RK3576/RV1126B多路视频 AI 开源引擎 CosmoEdge:从模型到交付,轻松搞定!
人工智能·opencv·计算机视觉·架构·课程设计
用户094248568033 小时前
第7章:Redis有序集合 ZSet 实战:排行榜与延时任务
redis·架构·源码
欣欣之王来了3 小时前
原始HTML插值:v-html指令的使用与安全风险
前端·学习·架构·项目·vue3教程
阿文和她的Key5 小时前
PHP2Shell事故四层拆解:AI找洞是小时级,披露协调还是邮件级
网络·人工智能·架构·php
forest_096 小时前
用Python复刻ClaudeDuet:主动式Agent四件套,定时晨报、后台巡检、危险动作审批(附完整可运行代码)
人工智能·python·架构·prompt·agi
幻智星科技7 小时前
多通道数据采集中collect_end信号的妙用
网络协议·架构·udp·硬件架构
海宇AI7 小时前
零信任架构实战:基于海宇行驶OCR证识别构建自动化租车车队行驶证电子档案网关
运维·人工智能·架构·自动化·1024程序员节
努力实干8 小时前
第 4 课:MVC、MVP 与 MVVM 架构
架构·mvc
Dawson Zhu9 小时前
【CUDA编程入门⑥】CPU多线程并行优化:OpenMP、NUMA与SIMD向量化
人工智能·语言模型·架构·aigc·agi