实现目标
- 保证获取锁和释放锁操作的原子性;
- 保证锁在应用异常时能自动释放;
- 保证多线程情况,不会被其他线程提前释放;
获取锁
public boolean requireLock(String lockKey, String requestId, int expireTime) {
return execute(jedis -> {
String result = jedis.set(custom(lockKey), requestId, "NX", "PX", expireTime * 1000);
if (LOCK_SUCCESS.equals(result)) {
return true;
}
return false;
});
}
释放锁
public boolean releaseLock(String lockKey, String requestId) {
return execute(jedis -> {
String script = "if redis.call('get', KEYS[1]) == ARGV[1] then return redis.call('del', KEYS[1]) else return 0 end";
Object result = jedis.eval(script, Collections.singletonList(custom(lockKey)), Collections.singletonList(requestId));
if (RELEASE_SUCCESS.equals(result)) {
return true;
}
return false;
});
}
资源使用
public <T> T execute(CodisCallBack<T> action) {
try (Jedis jedis = pool.getResource()) {
return action.doInRedis(jedis);
}
}