Skip to content

Seata

Apache Seata 为跨服务、跨数据源事务提供协调框架。它不能让网络调用天然具备本地数据库事务语义,而是通过事务协调、资源代理、幂等、补偿和状态持久化处理部分失败。

核心角色

角色职责
TC(Transaction Coordinator)维护全局与分支事务状态,协调提交或回滚
TM(Transaction Manager)定义全局事务边界,发起 Begin、Commit 或 Rollback
RM(Resource Manager)管理分支资源,注册分支并执行提交或回滚

模式对比

模式一阶段二阶段一致性与隔离适用场景
AT本地事务提交业务数据与 Undo Log异步清理或按 Undo Log 补偿最终一致;依赖全局锁改善写隔离支持本地事务的关系数据库、低业务侵入
XA数据库执行 XA PrepareXA Commit/Rollback一致性与隔离较强;资源锁持有更久数据源支持 XA,能接受阻塞与性能成本
TCC业务 Try 预留资源Confirm/Cancel由业务保证幂等、空回滚和防悬挂高性能、非关系资源或明确资源预留模型
Saga各参与者提交本地事务失败后执行补偿最终一致,通常不保证隔离长流程、跨组织或遗留系统

“AT 无业务侵入”仅表示不需要手写补偿接口,不代表没有数据库表、DataSource Proxy、SQL 限制、全局锁和运维成本。

AT 模式

一阶段在同一本地事务中完成业务 SQL、Before/After Image 与 undo_log 写入,然后提交本地事务。二阶段提交通常异步删除 Undo Log;回滚时校验数据并生成反向补偿 SQL。

  • 每个参与数据库创建符合版本要求的 undo_log 表。
  • SQL 类型、主键和数据库驱动必须在目标 Seata 版本支持范围内。
  • 全局锁只协调加入同一 Seata 全局事务的访问;未接入 Seata 的普通 SQL 仍可能产生并发冲突。
  • 回滚校验失败需要监控、告警和人工处理流程。

XA 模式

XA 利用数据库资源自身的 XA Prepare、Commit 和 Rollback。Prepare 后资源通常持续持锁到二阶段结束,隔离更完整,但长事务、TC 故障或网络抖动会放大锁等待。

yaml
seata:
  data-source-proxy-mode: XA

只有数据库与驱动真实支持 XA 才能使用;“主流数据库支持”不等于所有中间件、连接池和代理组合都经过验证。

TCC 模式

TCC 需要为每个分支实现 Try、Confirm、Cancel:

  • Try 检查并预留资源,保存可确认或取消的业务状态。
  • Confirm 幂等地把预留转为最终结果。
  • Cancel 幂等地释放预留,并处理 Try 未执行时的空回滚。
  • 防悬挂保证迟到的 Try 不会在 Cancel 之后再次占用资源。

库存冻结、余额冻结等具有显式预留状态的业务更适合 TCC。

Saga 模式

Saga 把长事务拆成一组本地事务,并为已成功步骤定义补偿操作。补偿不是数据库回滚:外部通知、价格变化、人工审批等副作用可能只能用新的业务动作抵消。

Saga 要明确状态机持久化、重试、超时、补偿失败、人工介入和幂等键。需要严格隔离的短事务通常不应仅因“参与服务较多”就选择 Saga。

Spring 接入

xml
<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-seata</artifactId>
</dependency>
yaml
seata:
  tx-service-group: order-tx-group
  registry:
    type: nacos
    nacos:
      server-addr: ${NACOS_SERVER_ADDR:127.0.0.1:8848}
      namespace: ${SEATA_NAMESPACE}
      group: SEATA_GROUP
      application: seata-server
  service:
    vgroup-mapping:
      order-tx-group: default
java
@GlobalTransactional(name = "create-order", rollbackFor = Exception.class)
public void createOrder(CreateOrderCommand command) {
    // 调用参与同一全局事务的分支服务
}

配置键和接入方式会随版本变化,不能继续复制 Seata 1.4.2 的 Starter 排除写法覆盖 BOM。

事务边界

  • 不把远程事务无限扩大;接口调用越多、耗时越长,失败概率和锁成本越高。
  • 设置全局与分支超时,并确保 RPC 超时、重试次数和事务超时协调。
  • RPC 自动重试必须有业务幂等键,不能只依赖数据库唯一键处理全部副作用。
  • MQ、缓存、搜索索引等异构资源通常更适合 Outbox、事务消息或 Saga,不应强行塞入数据库 AT。
  • 监控全局/分支事务数、回滚、超时、重试、Undo Log、Session Store 和 TC 可用性。