赞
踩
我们从官方文档开始来看看 文档地址,总结一下就下面几点了:
MultiLock
对象,实现了一组锁对象合并成一个大锁,统一进行加锁和释放锁,每个锁对象可能属于不同的redisson实例MultiLock
实例挂掉了,那么就可能导致这个multiLock一直处于被持有的状态,所以可以设置leaseTime和waitTime// 初始化三个锁
RLock lock1 = redissonClient.getLock("lockName1");
RLock lock2 = redissonClient.getLock("lockName2");
RLock lock3 = redissonClient.getLock("lockName3");
// 初始化三个锁的合并锁
RLock multiLock = redissonClient.getMultiLock(lock1, lock2, lock3);
// 获取锁
multiLock.lock();
// 释放锁
multiLock.unlock();
在看完BaseLock和FairLock之后,会冒出一些需要关注的点
从代码中可以看到,他是先初始化的三个RLock锁,然后再初始化的MultiLock,那么这个初始化过程做了什么呢?会有所好奇的
针对加锁这一块就会疑问比较多了,因为必须考虑到分布式锁的特性是如何去实现的?
既然是批量统一的锁住一批资源,且看代码中是先获取的多个RLock,那么这些锁是如何去进行的分组呢?需要不需要分组呢?如何做到统一锁定资源的?
整个加锁的过程是一个什么样子的?
最终Redis中存留的会有几个锁呢?
猜测应该是三个,只是和有类似CountDownLatch的机制,等待三个同时获取到锁,才会说获取锁成功,加锁成功返回
首先,这个锁是不是可重入锁?如果是可重入锁是如何去进行控制的呢?
在加锁成功之后,又是怎么样来维持的这个锁呢?如果是加锁三个的话,那不是得有三个watchdog在运行?
锁互斥倒是好理解,可以知道如果说都获取到了锁,也就是说统一资源加锁成功,那么这些资源就都被锁到了其他线程会加锁失败
有锁阻塞吗,其实每一个分组锁定的资源都是阻塞的形式
如果获取锁超时,那么其他已经获取到锁的客户端,会怎么停留?直到超时了,已经获取到锁的客户端怎么办呢?
如何判定加锁失败,是所有的都得成功吧
被动释放锁,应该分成几种吧
主动释放,也就是做完了工作自己来释放
获取MultiLock的时候,实际是获取的RedissonMultiLock
锁对象,接收的参数是前面初始化的RLock对象,MultiLock内部维护了一个RLock List属性
也就是说,这里的实际初始化是初始化了一个RLock列表
waitTime这样设置有什么好处呢?
锁的持有时间在设置了waitTime的情况下翻倍有什么含义
加锁实际上是很依赖RedissonLock的,只是做了一些算法逻辑上的控制
释放锁的整个流程就比较简单了,几乎是把RLock中释放锁的逻辑代码给抄过来的,就是做了一个遍历
protected RFuture<Void> unlockInnerAsync( Collection<RLock> locks, long threadId) { if (locks.isEmpty()) { return RedissonPromise.newSucceededFuture(null); } RPromise<Void> result = new RedissonPromise<Void>(); AtomicInteger counter = new AtomicInteger(locks.size()); for (RLock lock : locks) { lock.unlockAsync(threadId).onComplete((res, e) -> { if (e != null) { result.tryFailure(e); return; } if (counter.decrementAndGet() == 0) { result.trySuccess(null); } }); } return result; }
前面我们讲到,如果说master宕机的情况下,由于是异步复制的,可能存在key没有复制到slave上,就死掉了,就会导致了多客户端同时加锁成功的可能性
This object is deprecated. RLock operations now propagated to all Redis slaves.
弃用了……
从使用的角度来看,是继承自MultiLock的, 重写了其中的几个方法
failedLocksLimit--> lock.size - (locks.size()/2 + 1)
calcLockWaitTime --> Math.max(remainTime / locks.size(), 1)
多节点redis实现的分布式锁算法(RedLock):有效防止单点故障
假设有5个完全独立的redis主服务器
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。