zoukankan      html  css  js  c++  java
  • 幂等性

    幂等性的概念

    对于同一操作发起的请求(一次或者多次请求),任意多次执行对资源本身产生的影响均与一次执行产生的影响相同,不会因为多次相同操作而产生副作用。

    比如一个用户注册,点击“注册”,由于某些原因(比如服务器负载大),长时间转圈圈,你多次点击“注册”,这多次请求都是完全相同的,应该只插入一条用户记录,而不是点多次“注册”每次都插入一条用户记录。

    比如下单购买,点击“提交”,卡住了,什么破手机|网络,疯狂点“提交”,这多次请求完全相同,应该只产生一个订单,而不是每次点击都产生一个订单。

    http请求方式(restful)

    在其他条件不变的情况下(资源没有被其它操作修改):

    • get  查询,相同的查询操作,比如select username where id=1  from tb_user;执行多次,查询到的结果都是相同的,get是幂等的
    • post  插入,相同的插入操作,比如insert into tb_order (...) values (...);  执行多次,虽然可能会因为主键已存在、某个字段的值要唯一等原因插入失败,但每次都会尝试插入一条新纪录,如果满足约束,每次都会插入一条记录,结果可能不同(产生了新纪录),post不是幂等的
    • put  更新,相同的更新操作,比如update tb_user username='chy',age=20 where id=1;  不管执行多少次,id=1的这条记录,name都是chy,age都是20,结果都是相同的,put是幂等的
    • delete  删除,相同的删除操作,比如delete from tb_user where id=1 ,不管执行多少次,结果都是删除了id=1的记录,结果相同,delete是幂等的

    消息消费者与幂等性

    消息可能会被重复投递、消费,比如第一次投递的消息还在queue中,为确保消息投递的可靠性,延时又投递了一次消息,消费者应确保同一消息只进行一次消费。


    幂等常见的实现方式

    核心思想:

    使用唯一的业务单号来标识一个业务,如果业务单号相同,就认为是同一笔业务,只执行一次。(去掉重复的业务)

    存储执行过的业务的业务单号,先根据业务单号查询这笔业务是否已经执行过了,如果没执行过,才执行。

    如果系统是单线程的,查询单号、执行这笔业务2个过程都不用加锁;如果过多个线程并发访问执行过的业务单号(有读有写),就需要给执行过的业务单号加锁(幂等是查询时加锁),执行过程往往也需要给共享数据加锁。

    业务单号可以用流水号,也可以唯一id+指纹码,总之要能唯一标识一笔业务。

    比如order的id,只用id是可以唯一标识一个订单,但不能标识是这个order的增改删查哪个业务,也不能标识是这个order的第几次修改操作。需要再加一个指纹码,比如时间戳、业务规则什么的。

    1、数据库主键去重

    单独用一张tb_order_ handled来存储执行过的订单的业务单号,使用列no存储业务单号(主键、unique约束),外键order_id关联order表的id,

    执行业务时先select count(*) from tb_order_handled where no=xxx; 根据业务单号查询这笔业务是否已执行,数量为1表示有这条记录,这笔业务已处理过,不再处理;为0表示没处理过,就处理这笔业务。

    这种方式的缺点是增加了数据库IO次数,数据库性能很容易成为系统性能的瓶颈,往往需要分库分表把业务单号所在的表拆分出来,来提升数据库性能。

     如果这个服务只有数据库更新操作的话,也可以使用数据库的乐观锁(版本号机制)。

    2、分布式锁(推荐)

    把处理过的业务单号作为键值对的key,存储在redis上,处理业务时先查询redis上有没有这个key,有就说明处理过了,不再处理,没有就说明这笔业务没有处理过,开始处理。

    简单、且性能高,推荐。

    3、缓冲区

    把一段时间内要处理的业务都放到缓冲区中,先去掉重复的业务,再执行。

    缺点:处理有时延、不能马上返回处理结果。不太常用。

  • 相关阅读:
    不务正业系列-浅谈《过气堡垒》,一个RTS玩家的视角
    [LeetCode] 54. Spiral Matrix
    [LeetCode] 40. Combination Sum II
    138. Copy List with Random Pointer
    310. Minimum Height Trees
    4. Median of Two Sorted Arrays
    153. Find Minimum in Rotated Sorted Array
    33. Search in Rotated Sorted Array
    35. Search Insert Position
    278. First Bad Version
  • 原文地址:https://www.cnblogs.com/chy18883701161/p/12561765.html
Copyright © 2011-2022 走看看