• 接口幂等性详解


    概述

    所谓接口幂等性就是:在特定场景下,同一条件的多次接口调用,保证操作只执行一次,如果接口没有保证幂等性,在以下场景就会产生问题

    • 前端重复提交:用户进行注册、创建个人信息等操作,由于网络抖动导致页面没有及时响应,用户认为没有成功而多次点击提交按钮,发生重复提交表单请求
    • 接口超时重试:提供外部系统调用的接口,因为网络抖动等原因执行成功但没能及时响应,外部系统发起重试,导致重复调用
    • 消息重复消费:使用消息中间件时,消费者手动 ack 确认消息被正常消费时,消费者突然断开连接,已经执行的消息会重新放回队列,被其他消费者重新消费

    如何实现接口幂等性?

    1. 防重 Token 令牌

    具体流程如下:

    • 客户端获取 token,服务端将 token 保存在 redis 中,token 需保证全局唯一
    • 之后客户端发起请求时必须携带 token
    • 服务端校验 token,如果成功则执行业务,并删除 redis 中的 token,否则为重复操作,直接返回结果

    这种方式需保证同一请求都携带同一 token,比如同一订单的支付操作都使用同一 token 请求。另外,在并发情况下,Redis 查找数据与删除需要保证原子性,可以使用或 Lua 脚本保证

    2. 使用 Redis 实现

    这种实现方式是基于 redis 的 setnx 命令实现的,作用是如果 key 不存在,将 key 赋值为 value 并返回 1,若 key 已存在,则不做操作并返回 0

    具体流程如下:

    • 客户端请求服务端,将能代表这次请求的唯一标识以 setnx 的方式存入 redis,并根据业务设置相应的超时时间
    • 如果设置成功,代表是第一次请求,执行后续业务逻辑
    • 如果设置失败,代表已经执行过请求,直接返回

    redis 是单线程的,所以不会有并发问题

    3. 加锁实现

    具体流程如下:

    • 客户端请求服务端,对能代表这次请求的唯一标识加锁,保证同一时刻同一请求只有一个能被执行
    • 服务端根据唯一标识判断是否第一次请求,比如查询数据库是否已存在该唯一标识的记录,或者该唯一标识对应记录状态是否为【已完成】
    • 如果是第一次请求,执行后续业务逻辑,否则直接返回

    4. 幂等表

    加锁会影响性能,我们可以建一张幂等表,为能代表这次请求的唯一标识建立唯一约束

    具体流程如下:

    • 客户端请求服务端,服务端会将本次请求的信息插入幂等表
    • 因为有唯一约束,如果幂等表中不存在本次请求记录,则插入成功,执行后续业务逻辑,插入失败,则直接返回

    使用这种方式,每次请求都会幂等表新建一条记录,为了避免表数据过大,可以定期进行清理,或者使用流水表来代替幂等表。使用插入而不是查询,也能有效避免并发问题


    __EOF__

  • 本文作者: 低吟不作语
  • 本文链接: https://www.cnblogs.com/Yee-Q/p/18012149
  • 关于博主: 评论和私信会在第一时间回复。或者直接私信我。
  • 版权声明: 本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
  • 声援博主: 如果您觉得文章对您有帮助,可以点击文章右下角推荐一下。
  • 相关阅读:
    策略模式详解+代码案例
    sentinel规则
    怎么保护公司文件安全
    PyTorch深度学习实战(3)——使用PyTorch构建神经网络
    623. 在二叉树中增加一行(难度:中等)
    LeetCode952三部曲之三:再次优化(122ms -> 96ms,超51% -> 超91%)
    Axelar、J.P.Morgan Onyx、Apollo 完成概念验证,向跨区块链自动化投资领域探索
    文件系统(四):FAT32文件系统实现原理
    【C++】运算符重载 ⑩ ( 下标 [] 运算符重载 | 函数原型 int& operator[](int i) | 完整代码示例 )
    全新升级的AOP框架Dora.Interception[汇总,共6篇]
  • 原文地址:https://www.cnblogs.com/Yee-Q/p/18012149