橙与卿欢 2021-06-04 18:32 采纳率: 0%
浏览 23

redis使用lua脚本实现锁,jmeter测试,值总比预想的值少,请求丢失还是别的什么问题???

 通过jmeter测试线程为50,循环2次,总共100请求,预计结果为100,但是得到的是98...,有没有大佬帮我看看问题在哪.

监控表格得到的请求都是成功的

 

 接口的代码:

    /**
     * 使用lua脚本,防止误删,不能解决业务未执行完成的锁过期问题.
     * @return
     */
    @ApiOperation(value = "redis-使用lua脚本防止误删-set")
    @GetMapping("/noErrorDelLock")
    public Result testNoErrorDelLock() {
        // 上锁,set,设置唯一值
        String uuid = UUID.randomUUID().toString();
        // 访问的数据,预先在redis设置num的值,num必定存在
        // num的初始在redis设置为0。
        String str = "num";
        String lockKey = "lock:" + str; // 锁住的是访问的数据。
        // 获取锁
        Boolean lock = redisTemplate.opsForValue().setIfAbsent(lockKey, uuid,10, TimeUnit.SECONDS);

        // 获取锁成功、查询num的值
        if (lock) {
            // 获取数据
            redisTemplate.opsForValue().increment(str);
            // 释放锁,只能释放自己的锁
            // lua脚本
            String script = "if redis.call('get',KEYS[1]) == ARGV[1] then return redis.call('del',KEYS[1]) else return 0 end";
            // 使用redis执行lua脚本
            DefaultRedisScript<Long> redisScript = new DefaultRedisScript<>();
            redisScript.setScriptText(script);
            // 设置一下返回值类型 为long
            // 因为删除判断的时候返回的0,给其封装为数据类型,如果不封装那么默认返回String类型。
            // 那么返回字符串与0会有发生错误。
            redisScript.setResultType(Long.class);
            // 第一个要是script,第二个需要判断的key,第三个就是key所对应的值
            redisTemplate.execute(redisScript, Arrays.asList(lockKey), uuid);
        }else{
            // 获取锁失败、每隔0.1s再获取
            try{
                Thread.sleep(100);
                testLock();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        return RestResult.success(ResultCodeEnum.SUCCESS, redisTemplate.opsForValue().get(str));
    }

最后redis得到的值:

  • 写回答

2条回答 默认 最新

  • 橙与卿欢 2021-06-04 18:39
    关注

    直接手动释放锁都不会出问题,而且请求次数也多了很多,但是使用lua脚本就出问题了。。。。。。

    // 释放锁,只能释放自己的锁
    String lockUUID = (String) redisTemplate.opsForValue().get(lockKey);
    if (uuid.equals(lockUUID)) {
        redisTemplate.delete(lockKey);
    }
    评论

报告相同问题?

悬赏问题

  • ¥15 软件供应链安全是跟可靠性有关还是跟安全性有关?
  • ¥15 电脑蓝屏logfilessrtsrttrail问题
  • ¥20 关于wordpress建站遇到的问题!(语言-php)(相关搜索:云服务器)
  • ¥15 【求职】怎么找到一个周围人素质都很高不会欺负他人,并且未来月薪能够达到一万以上(技术岗)的工作?希望可以收到写有具体,可靠,已经实践过了的路径的回答?
  • ¥15 Java+vue部署版本反编译
  • ¥100 对反编译和ai熟悉的开发者。
  • ¥15 带序列特征的多输出预测模型
  • ¥15 Python 如何安装 distutils模块
  • ¥15 关于#网络#的问题:网络是从楼上引一根网线下来,接了2台傻瓜交换机,也更换了ip还是不行
  • ¥15 资源泄露软件闪退怎么解决?