微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

Redisson 分布式锁简单应用

    RLock rLock = redissonClient.getLock("lockName");// 可以看做是获取一个连接
    try {
        // 尝试加锁 愿意等待的时长 waitTime ; 加锁成功后自动释放锁的时长 leaseTime,大于0时不论加锁业务是否处理完毕都会释放锁 
        boolean locked = rLock.tryLock(1000, 2000, TimeUnit.MILLISECONDS);// 尝试加锁
        if(locked){
            // todo 加锁成功需要处理的业务处理
        }else{
            // todo 加锁失败需要处理的业务
        }
    }catch (Exception e) {// 
       throw e; // 加锁失败 和 业务处理失败后 需要做的事情
    } finally {
        try{
            rLock.unlock();// 这个很要命 手动释放锁  unlock 异常后是否需要
         }catch(Exception e){
              // 释放锁失败 要做的处理(忽略异常 还是 继续抛出异常,还是 强制释放锁)  
          }
    }

一、先做点解释

1、参数 

        waitTime  为了获取锁愿意等待的时长 <= 0 不愿意等待,即没有获取到锁时直接返回false

        leaseTime 加锁成功后自动释放锁的时长,>0 时 不论锁定的业务是否执行完毕都会在这个时间到期时释放锁---这个很要命;=-1表示这个锁不会自动释放必须手动释放,看门狗每10秒(认配置)延期一次锁(实际是重置锁的过期时间为30秒:认配置)

2、上图伪代码仅供参考

二、结论

        1、根据自身业务 谨慎并合理设置 waitTime  和 leaseTime 值 ;

        2、finally 中一定要 手动释放锁 rLock.unlock(); ---锁定的资源在业务处理完毕后尽快释放,不论是否设置了自动释放锁;

三、加锁的lua脚本

"if (redis.call('exists', KEYS[1]) == 0) then " +
    "redis.call('hincrby', KEYS[1], ARGV[2], 1); " +
    "redis.call('pexpire', KEYS[1], ARGV[1]); " +
    "return nil; " +
    "end; " +
    "if (redis.call('hexists', KEYS[1], ARGV[2]) == 1) then " +
    "redis.call('hincrby', KEYS[1], ARGV[2], 1); " +
    "redis.call('pexpire', KEYS[1], ARGV[1]); " +
    "return nil; " +
    "end; " +
    "return redis.call('pttl', KEYS[1]);"

KEYS[1]=lockName,ARGV[2]=hash中的key=redisson客户端节点id+线程id,ARGV[1]=锁的过期时间

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐