TCC事务
TCC(Try-Confirm-Cancel)是分布式事务中性能最好、控制粒度最细,但开发成本最高的模式。
一、TCC 核心原理
TCC 将业务逻辑拆分为三个阶段,需要开发者手动实现三个接口:
流程如下:
- Try 阶段(尝试/预留)
做什么:检查业务资源,预留/冻结资源。
例子:冻结账户余额(不扣减)、锁定库存(不扣减)。
要求:幂等、允许失败。 - Confirm 阶段(确认/执行)
做什么:真正使用 Try 阶段预留的资源。
例子:扣除已冻结的余额、扣减已锁定的库存。
要求:必须成功(如果 Try 成功,Confirm 不应该失败,否则需要人工介入),幂等。 - Cancel 阶段(取消/回滚)
做什么:释放 Try 阶段预留的资源。
例子:解冻余额、释放锁定库存。
要求:幂等。
1 | [TM 全局事务] |
二、TCC vs AT 模式对比
| 特性 | AT 模式 (Seata 默认) | TCC 模式 |
|---|---|---|
| 侵入性 | 无侵入 (SQL 解析) | 高侵入 (需改业务代码,写 3 个方法) |
| 一致性 | 最终一致性 (依赖 undo_log) | 最终一致性 (依赖业务补偿) |
| 隔离性 | 全局锁 (读写冲突) | 无全局锁 (业务隔离) |
| 性能 | 一般 (高并发下有锁竞争) | 高 (适合高并发) |
| 开发成本 | 低 (加注解即可) | 高 (需处理幂等、空回滚、悬挂) |
| 适用场景 | 内部微服务,中低并发 | 核心链路,高并发,跨语言 |
三、使用场景
不要为了炫技而用 TCC。 请遵循以下决策路径:
- 首选 AT 模式:90% 的场景,AT 模式足够用,开发快,维护成本低。
- 遇到性能瓶颈时:如果 AT 模式的全局锁导致数据库并发上不去(例如秒杀、热点账户),再考虑 TCC。
- 核心资金链路:支付、转账等场景,需要业务层面的精细控制(如冻结资金),TCC 更合适。
- 非 Java 语言:如果事务参与者包含 Go/Python 服务,AT 模式(依赖 Java SQL 解析)无法使用,必须用 TCC。
四、TCC代码实战
4.1 配置依赖
各个微服务引入
1 | <dependency> |
4.2 代码入口添加全局事务
入口
1 |
|
被调用方
1 | (name = "doSave", // 动作名称,全局唯一 |
4.3 接口测试
发送测试报文,可以看到seata server 日志信息
