接口幂等性方案
幂等性是指对同一操作的多次执行所产生的影响与一次执行的影响相同。在接口设计中,保证幂等性非常重要,特别是在分布式系统中。
常见幂等性解决方案
1. 唯一标识符(Token机制)
-
实现方式:
- 客户端先请求获取一个唯一token
- 服务端生成并存储token(可设置有效期)
- 客户端携带token发起业务请求
- 服务端验证token是否存在,存在则处理请求并删除token
-
优点:实现简单
-
缺点:需要额外一次交互获取token
2. 乐观锁
- 实现方式:
- 数据表中增加版本号字段
- 更新时检查版本号是否匹配
- 更新成功后版本号递增
UPDATE table SET value=newValue, version=version+1 WHERE id=#{id} AND version=#{oldVersion}
- 适用场景:更新操作
3. 唯一索引/约束
-
实现方式:
- 为业务关键字段创建唯一索引
- 插入重复数据时会报错
- 捕获异常并返回成功
-
适用场景:创建操作
4. 状态机
-
实现方式:
- 定义业务状态流转规则
- 只有符合规则的流转才允许执行
- 例如订单状态只能从"待支付"→"已支付",不能重复支付
-
适用场景:有状态流转的业务
5. 分布式锁
- 实现方式:
- 使用Redis或Zookeeper实现分布式锁
- 操作前获取锁,操作完成后释放
- 设置合理的锁超时时间
// 伪代码
if (redis.setnx(key, value, expireTime)) {
try {
// 处理业务
} finally {
redis.del(key);
}
}
6. 去重表
- 实现方式:
- 创建请求记录表
- 每次请求前插入记录(唯一业务ID)
- 插入成功则处理,失败则认为是重复请求
实际应用建议
- 根据业务场景选择:不同业务场景适合不同的幂等方案
- 组合使用:可以组合多种方案提高可靠性
- 前端配合:按钮防重、loading状态等减少重复提交
- 合理设计API:
- GET查询天然幂等
- PUT更新适合用幂等设计
- POST创建需要额外处理
幂等性实现示例(Token机制)
// 生成token接口
@GetMapping("/token")
public String generateToken() {
String token = UUID.randomUUID().toString();
redisTemplate.opsForValue().set(token, "1", 5, TimeUnit.MINUTES);
return token;
}
// 业务接口
@PostMapping("/order")
public Result createOrder(@RequestHeader("X-Token") String token, OrderDTO dto) {
// 检查token是否存在
if (!redisTemplate.hasKey(token)) {
return Result.fail("重复提交或token已过期");
}
// 删除token
redisTemplate.delete(token);
// 处理业务逻辑
return orderService.createOrder(dto);
}
保证接口幂等性可以显著提高系统的可靠性和用户体验,特别是在网络不稳定或用户重复操作的情况下。
1360

被折叠的 条评论
为什么被折叠?



