锁的实现简述:
- 线程同步队列 WaitThreadQueue ,利用redis list实现,存放当前正在等待锁的线程
- 锁等待超时时间 ThreadSet ,利用redis zset实现,hkey存放 线程Id score存放等待锁的超时时间
- 锁持有 ThreadHash 利用redis hash 实现 hkey 存放 线程Id hvalue存放 重入次数
- 线程进入等待锁阶段以及线程被唤醒 利用redis 发布订阅
用法:
- 直接用lock()或者 lock(leaseTime, …)或者tryLock(waitTime…)方法,优点是获取锁及时,但是如果锁竞争比较激烈、会有大量请求 redis 的发布订阅 (保持长连接)对redis 服务器有在文件句柄限制(最大文件句柄65535),而且发布订阅当订阅数越来越多时,redis是挨个给客户端发送消息,获取锁会越来越不及时。
- 用循环执行tryLock的方法获取锁,每次tryLock后sleep一段时间。tryLock没有发布订阅 ,只是单纯的获取锁。这种用法不需要保持保持长连接,对redis压力小,但是获取锁不及时,不适用于对响应时间有严格要求的服务。同时,这种方法对业务服务器的CPU也有压力,不过业务服务器扩容相对于redis 服务器扩容更便利。