如何保证服务的幂等性
1.概念:
接⼝的幂等性实际上就是接⼝口可重复调⽤用,在调⽤用⽅方多次调⽤用的情况下,接⼝口最终得到的结果是⼀一致的。有些接口可以天然的实现幂等性,⽐比如查询接⼝,对于查询来说,你查询⼀一次和两次,对于系统来说,没有任何影响,查出的结果也是⼀一样。
2、GET幂等:
值得注意,幂等性指的是作⽤用于结果⽽而⾮非资源本身。怎么理理解呢?例例如,这个HTTP GET⽅方法可能会每次
得到不不同的返回内容,但并不不影响资源。
3、POST⾮幂等:
因为它会对资源本身产⽣生影响,每次调⽤用都会有新的资源产⽣,因此不满足幂等性。
4、如何保证幂等性:
1、全局唯⼀一id:如果使⽤用全局唯⼀一ID,就是根据业务的操作和内容⽣生成⼀一个全局ID,在执⾏行行操作前先根据这个全局唯
⼀ID是否存在,来判断这个操作是否已经执⾏行行。如果不存在则把全局ID,存储到存储系统中,比如数据库、redis等。如
果存在则表示该⽅方法已经执行。
2、去重表:这种⽅方法适⽤用于在业务中有唯⼀一标的插⼊入场景中,⽐比如在以上的⽀支付场景中,如果⼀一个订单只会⽀支付⼀一
次,所以订单ID可以作为唯⼀一标识。这时,我们就可以建⼀一张去重表,并且把唯⼀一标识作为唯⼀一索引,在我们实现时,
把创建⽀支付单据和写⼊入去去重表,放在⼀一个事务中,如果重复创建,数据库会抛出唯⼀一约束异常,操作就会回滚。
3、插⼊入或更更新:这种⽅方法插⼊入并且有唯⼀一索引的情况,⽐比如我们要关联商品品类,其中商品的ID和品类的ID可以构成
唯⼀一索引,并且在数据表中也增加了了唯⼀一索引。这时就可以使⽤用InsertOrUpdate操作。在mysql数据库中如下:
insert into goods_category (goods_id,category_id,create_time,update_time)
values(#{goodsId},#{categoryId},now(),now())
on DUPLICATE KEY UPDATE
update_time=now()
4、多版本控制:这种⽅方法适合在更更新的场景中,⽐比如我们要更新商品的名字,这时我们就可以在更新的接⼝中增加⼀
个版本号,来做幂等
5、状态机控制:这种⽅方法适合在有状态机流转的情况下,⽐比如就会订单的创建和付款,订单的付款肯定是在之前,这
时我们可以通过在设计状态字段时,使⽤用int类型,并且通过值类型的⼤大⼩小来做幂等,⽐比如订单的创建为0,付款成功为
100。付款失败为99