类似优惠券系统问题排查

简介: 问题排查与解决方案

总结就是 所有敏感的操作 类似跟钱挂钩的 比如发放优惠券的前提就是判断到发放 我们一般都是让一系列操作是原子性 并且别人获取不到这个锁

如果数据不敏感 类似点赞的 那么没有必要 因为一致性必须牺牲高可用的

工厂模式帮我们自动根据传入参数自动执行不同的函数

策略模式帮我们设定了不同的方案 根据传入的参数选择不同的参数去选择不同的方法

首先大体确定问题范围属于并发引起的问题 所以很容易就想到锁了

超卖问题的话

我们只需要确定为什么会超卖

无非就是再发放优惠券的时候没有确定是否已达用户领取上限 或者是 优惠券总发放上限

所以很好解决 无非就是 用上乐观锁的思想 再发放的sql语句加上where条件判断而已

锁失效问题

查询 判断 新增满足这三步之后才会发放优惠券

逻辑上确实没问题 但是我们考虑的只是单机

如果我们并发前提下 A线程执行新增之前 B执行到判断了

这个时候就会出现 同时满足的情况

所以实际上也就是 查询判断新增这三步核心逻辑 我们分开写了 没有使他们同时执行 不具备原子性,

所以我们直接考虑用 Synchronized实现

锁方法太大了 太慢了 所以我们考虑锁方法块 锁的对象由于我们知道Long存在常量池复用-127到128的对象

所以不能直接锁long 要锁实际值 所以使用apiuserId.toString().intern()来最终解决这个问题

事务边界问题

如果我们开启事务之后 才获取锁 然后释放锁 再提交事务

这个时候就会出现释放锁之后 还没提交事务 其他线程拿到锁 访问了资源 也就是脏读问题

那么只需要换个思考方式 那么我就提交好了再释放锁 不就可以了嘛

所以很简单 就是先获取锁 开启事务 提交事务 释放锁

事务失效问题

那么都用到事务了 事务肯定就会存在失效的情况

排查

1.事务方法非public修饰 spring会有方法判断方法如果不是public进不去

2.非事务方法调用事务方法 因为事务底层是aop生成动态代理 我们当前类调用实际上是this去调用 这个类似成员变量赋值都是this.set get

那么我们非事务 自然aop不会帮我们生成动态代理对象 所以也就不会检测到事务了 所以也就失效了 解决方案就是 手动调用aop对象去调用方法 也就是 aop(动态代理对象).方法名

3.事务方法的异常被捕获 被捕捉了 自然没异常就不会回滚

4事务异常类型不对 类型不对 也就不会检测到 也就相当于没回滚了

5事务传播行为不对 事务之间是有隔离性的 那么A回滚了 是不会影响B的 因为B是独立于A的 当然如果这里是嵌套事务的话 那么就大的会影响小的 小的不会影响大的

6.没有被Spring管理 如果类都没被spring管理 aop都没办法帮你创建代理对象 那就肯定失效了

集群锁失效问题

我们使用的Synchronized底层是基于jvm的锁监视器去做的

当我们部署了多个实例 那么就会有多个jvm

所以自然每个jvm的锁监视器就不一样了 那么这个时候实际上 就会有多个user2的锁

解决方案 类似seata记录表 不再基于jvm的锁监视器 而是基于数据库表 也就是设置分布式锁

分布式锁问题

我们一开始是加锁后再设置过期时间 那么如果加锁后宕机了呢 对吧 实际上还是回到两个操作是分开的 解决方案就是让两个操作有原子性 一起执行

加锁同时设置过期时间指令:SET key value NX EX seconds

那么设置了过期时间后 就会出现当线程1阻塞的时候 锁A过期了

所以这个时候别的线程2就可以获取到锁A 这个时候 开始执行业务

但是这个时候线程1醒过来了 继续删除释放锁 就会导致线程3可以拿到锁了 就会出现又并发了

解决方案 我们设置线程名字为锁key 比如 key为 Thread1 加上userid 这种唯一标识

删除之前判断是否当前线程的 如果不是就不删

记得把判断跟删除 作为一个操作 不然又会出现极端情况了

后面我们还使用了redisson来作为我们的锁

因为他支持重入,看门狗等 而且使用更加简单

还引入了工厂模式来帮我们自然化 根据用户传入的锁类型支持不同的获取锁的对象

后面引入策略模式来帮我们解决多种获取失败方案 解决代码冗余问题

相关文章
|
6月前
|
机器学习/深度学习 监控 对象存储
视觉智能平台常见问题之购买了资源包显示已超限如何解决
视觉智能平台是利用机器学习和图像处理技术,提供图像识别、视频分析等智能视觉服务的平台;本合集针对该平台在使用中遇到的常见问题进行了收集和解答,以帮助开发者和企业用户在整合和部署视觉智能解决方案时,能够更快地定位问题并找到有效的解决策略。
|
6月前
|
数据采集 存储 监控
利用API接口进行竞品价格监控
在电子商务和零售行业,了解竞争对手的定价策略对于保持市场竞争力至关重要。随着技术的发展,通过编程接口(API)获取商品详情成为企业监控竞品价格的有效手段。本文将详细介绍如何利用API接口实现竞品价格监控的流程和策略。
|
小程序
优惠券流程
优惠券流程
313 0
|
存储 SQL 缓存
大厂的优惠券系统是如何设计的?
1 Scenario 场景 电商系统的促销手段(Electronic Commerce Systems): 优惠券 拼团 砍价 老带新
1201 0
|
数据挖掘 BI 开发者
异常流量渠道订单明细诊断|学习笔记
快速学习异常流量渠道订单明细诊断
108 0
异常流量渠道订单明细诊断|学习笔记
|
API
云市场资源包额度预警设置及使用明细查询操作指导
阿里云云市场是软件交易及交付平台。云市场致力于为中小型企业提供全方面的 IT 服务,大幅降低企业互联网化成本, 打造企业上云、产品选购、服务落地、交易一体化流程。共同构建云上生态,让信息化更简单。作为阿里云的战略发展点,承接着中国云生态各个链条产品的落地。云市场平台提供完备的服务监管来保障用户利益,并把更多的产品、品牌及销售资源赋能商家。客户在购买使用云市场服务后为了避免当资源包耗尽时,面临服务不可用风险。通常有设置资源包额度预警和查看使用明细得需求。但是由于云市场控制台的不熟悉,往往不知如果进行额度预警的调整及设置。本文简单介绍设置资源包额度预警和查看资源包用量明细操作步骤,以供参考
588 0
云市场资源包额度预警设置及使用明细查询操作指导
|
消息中间件 RocketMQ 开发者
下单异常问题演示|学习笔记
快速学习下单异常问题演示
106 0
下单异常问题演示|学习笔记
|
运维 监控 NoSQL
一次线上问题排查所引发的思考
之前或多或少分享过一些内存模型、对象创建之类的内容,其实大部分人看完都是懵懵懂懂,也不知道这些的实际意义。
|
消息中间件 RocketMQ 开发者
下单基本流程小结|学习笔记
快速学习下单基本流程小结
158 0