秒杀优化: 记录一次bug排查

现象

做一人一单的时候,为了提升性能,需要将原来的业务改造成Lua脚本加Stream流的方式实现异步秒杀。

代码改造完成,使用Jmeter进行并发测试,发现redis中的数据和预期相同,库存减1,该用户也成功添加了进去,但是打开数据库的订单表,发现这条数据没有添加进去。

排查

开始以为是consumer没有收到消息,检查了一遍队列名称,consumerGroup,consumer名称都是没问题的。

然后在子线程中打了断点,然后再次启动,发现报出了一个空指针异常,定位到了是创建对象createVoucherOrder2当中Long userId = UserHolder.getUser().getId()中user居然是空,token也没失效。

emmm,最后发现是createVoucherOrder2是在子线程中调用的,已经切换线程了,自然不能再从ThreadLocal里获取对象了。

队列中存在的订单对象中包含了userId,所以正确的做法应该是从订单对象里面取。

真的是一个很容易忽略的错误。

贴相关代码

java 复制代码
        private void createVoucherOrder2(VoucherOrder voucherOrder) {
            //添加逻辑:该用户是否已经已经下过单了
            //防止黄牛恶意刷单 但是会存在和超卖相同的问题 同一个用户但是超卖了三张票
            Long userId = voucherOrder.getUserId();
            RLock lock = redissonClient.getLock("lock:order:" + userId);
            boolean tryLock = lock.tryLock();

            if (!tryLock) {
                log.error("不允许重复下单");
                return;
            }
            try {
                Long voucherId = voucherOrder.getVoucherId();
                //3.查询订单
                Integer count = query()
                        .eq("user_id", userId)
                        .eq("voucher_id", voucherId)
                        .count();
                //4.校验一人一单
                if (count > 0) {
                    log.error("无法重复下单");
                    return;
                }
                //5.库存扣减 超减问题并发量3000的情况下 超卖10张
                boolean success = seckillVoucherService.update()
                        .setSql("stock= stock -1")
                        .eq("voucher_id", voucherId)
                        .gt("stock", 0).update();

                if (!success) {
                    log.error("库存不足,下单失败");
                    return;
                }
                //6.添加订单
                voucherOrderService.save(voucherOrder);
            }catch (Exception e){
                log.error("下单失败{}",e.getMessage());
            }finally {
                lock.unlock();
            }
        }

emmm

再次启动,Mysql订单表成功添加一条数据。

Jmeter汇总报告

相关推荐
golang学习记15 小时前
VS Code 新UI被曝重大bug:菜单栏消失了
vscode·bug
j7~18 小时前
【软件测试】(概念篇)《需求的概念,测试用例(case),软件错误(bug),开发模型以及测试模型》---详解
软件测试·bug·敏捷模型·开发模型·测试模型·测试中需求的定义·软件的生命周期
冰水不凉2 天前
CodeX 在 Ubuntu 下 vscode 插件的 bug 问题
vscode·ubuntu·bug
flower_drop2 天前
基于 WebUSB 与 CDP:在浏览器端实现 Android 设备通信与无证书抓包实践
android·chrome·测试工具·adb·bug·edge浏览器
lytao1233 天前
90% 覆盖率不等于没 Bug:用风险配置测试组合
前端·javascript·bug·软件工程
Joker-Full-stack3 天前
higress Grafana生产事故复盘:Loki 2.9 WAL 竞态 Bug 导致 5 天审计日志消失
bug·grafana·higress
我星期八休息6 天前
软件测试—从认识到BUG
考研·安全·bug
hulihutu447 天前
拒绝延期、bug、货不对板:2026 管理系统定制开发落地保障手册
github·bug·鸿蒙系统·数据库管理员
Rain5097 天前
谁动了我的 URL?——记一次微前端“灵异 Bug“的排查实录
前端·vue.js·人工智能·前端框架·bug·ai编程