redis分布式锁和redisson实现分布式锁

redis结合jedis实现自带分布式锁

第一步
在这里插入图片描述
第二步
在这里插入图片描述

        System.out.println("ip为"+ip+"的同学"+Thread.currentThread().getName()+"进入了商品详情的请求");
        PmsSkuInfo pmsSkuInfo = new PmsSkuInfo();
        //获得jedis链接
        Jedis jedis = redisUtil.getJedis();


        //sku的key
        String skuKey="sku:"+skuId+":info";
        //分布式锁
        String skuLock="sku:"+skuId+":lock";



        //查询缓存
        String skuIdJson = jedis.get(skuKey);

        //如果取到值 把json转换为对象 使用 fastJson
        if(StringUtils.isNoneBlank(skuIdJson)){
            System.out.println("ip为"+ip+"的同学"+Thread.currentThread().getName()+"从缓存中拿数据");
            pmsSkuInfo= JSON.parseObject(skuIdJson, PmsSkuInfo.class);
        }else {
            //如果缓存中没有从数据库取  这又会遇见一个问题 缓存击穿

            //设置分布式锁
//            String token = UUID.randomUUID().toString();
//            String OK=jedis.set(skuLock,token,"nx","ex",10);
            RLock lock = redisson.getLock(skuLock);

            try {
                boolean result = lock.tryLock(100, 30, TimeUnit.SECONDS);

                if(result){
                    //设置成功有权在10秒内访问数据库
                    System.out.println("ip为"+ip+"的同学"+Thread.currentThread().getName()+"获得分布式锁有权在10秒内访问数据库");
                    pmsSkuInfo=getSkuByIdFromDb(skuId);
                    if(null!=pmsSkuInfo){
                        //mysql数据存入 redis缓存
                        jedis.set(skuKey,JSON.toJSONString(pmsSkuInfo));  //正常来说需要设置过期时间
                    }else{
                        //防止缓存穿透 数据库不存在的sku
                        //解决方法,将 null或者 ""设置给redis
                        jedis.setex(skuKey,60*3,JSON.toJSONString(""));
                    }
                    System.out.println("ip为"+ip+"的同学"+Thread.currentThread().getName()+"释放锁");


                }else{
                    //设置锁失败,自旋(该线程休眠几秒重新访问本方法)
                    try {
                        Thread.sleep(3000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    System.out.println("ip为"+ip+"的同学"+Thread.currentThread().getName()+"开始自旋");
                    return getSkuById(skuId,ip);  //开始自旋重新访问本方法
                }


            } catch (InterruptedException e) {
                e.printStackTrace();
            }finally {
                lock.unlock(); //释放锁
            }

        }
        //关闭jedis
        jedis.close();
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值