Files
junhong_cmp_fiber/openspec/changes/fix-order-activation-idempotency/design.md
huang b02175271a
All checks were successful
构建并部署到测试环境(无 SSH) / build-and-deploy (push) Successful in 5m39s
feat: 实现企业设备授权功能并归档 OpenSpec 变更
- 新增企业设备授权模块(Model、DTO、Service、Handler、Store)
- 实现设备授权的创建、查询、更新、删除等完整业务逻辑
- 添加企业卡授权与设备授权的关联关系
- 新增 2 个数据库迁移脚本
- 同步 OpenSpec delta specs 到 main specs
- 归档 add-enterprise-device-authorization 变更
- 更新 API 文档和路由配置
- 新增完整的集成测试和单元测试覆盖
2026-01-29 13:18:49 +08:00

1.6 KiB
Raw Blame History

订单激活幂等性修复 - 设计

目标

  1. 同一订单被重复支付/重复回调/重复请求时,只会激活一次套餐使用记录。
  2. 重复请求返回“幂等成功”(不报错,不重复激活)。
  3. 避免因并发导致的重复插入。

方案

1) 以状态机作为幂等门闸

将订单支付状态从 pending 变更为 paid 时使用条件更新:

  • UPDATE tb_order SET payment_status=paid,... WHERE id=? AND payment_status=pending
  • RowsAffected == 0
    • 视为订单已被处理(可能已支付/已取消/已退款)
    • 对“已支付”场景直接返回成功(幂等成功)
    • 对“非待支付且非已支付”场景返回对应业务错误(例如已取消不允许支付)

这样可以确保并发下只有一个请求能“拿到激活资格”。

2) 激活逻辑只在首次成功支付后执行

activatePackage 只在上述条件更新成功后执行;并确保激活过程内的数据读取使用同一个事务 tx(避免出现读取不一致或部分写入)。

3) 防御性约束(可选但推荐)

tb_package_usage 增加唯一约束(示例):

  • 同一订单下,同一 package_id 只能有一条 usage
  • order_id + package_id 为主(按当前业务:一个订单对应一个资源,且一次购买不应重复同套餐)

如果未来允许同订单同套餐多份购买,则需要同时引入 quantity 或 usage 的明细拆分策略,再调整唯一约束。

验收标准

  • 重复调用钱包支付/支付回调接口,不会重复生成 tb_package_usage 记录。
  • 幂等重复请求返回成功。
  • 新增测试通过。