在计算机中,锁是用于解决资源竞争问题。在单机(单进程)环境下, 锁可以使用操作系统提供的同步原语实现。 但在分布式环境下,操作系统提供的同步原语就失效了, 需要一个分布式锁。其原理是需要一个分布式锁管理器[1],提供进程级别访问共享资源的互斥性。本文主要讨论基于Redis实现的分布式锁。
分布式锁的使用场景
Martin Kleppmann 在他的博客 How to do distributed locking[2] 中对分布式锁的使用场景做了非常好的概括。从一个更高层次来讲,在一个分布式应用中,使用分布式锁主要有两个原因:效率和正确性。
- 效率:获取分布式锁可以避免相同的任务被处理两次。如果锁失败,带来的结果就是对某一个子任务多做了一次,其影响完全取决于具体业务场景。比如为了提高消息PUSH效率,需要按用户进行分片,然后每个任务获取一个锁后处理对应的分片,如果锁失败,会造成重复给用户PUSH。
- 正确性:获取分布式锁是为了防止进程对分布式系统中的资源并发访问而导致系统的状态出现混乱。如果锁失败,两个节点并发的访问同一个共享资源,可能造成数据的不一致性,如文件损坏或数据丢失等。