应用场景:
当多个应用进程(客户端)需要互斥地访问共享资源时,可以使用分布式锁。其中Redis官方权威提出了RedLock。Java中可使用Redssion提供的实现。
注意点:
- 互斥,保证任何时刻只能有一个客户端 获取到锁;
- 效率之死锁,保证获取到锁的客户端即使在出现网络分区或者宕机的情况下,也能释放掉锁;
- 效率之容错,保证只要大多数Redis节点正常工作,客户端就能正常获取到锁和正常释放锁。
原理:
获取锁:
SET resource_name my_random_value NX [EX|PX] 30000
Redssion中的实现使用了Hash, 可重入:
if (redis.call(‘exists’, KEYS[1]) == 0)
then redis.call(‘hset’, 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