写点什么

redis 实现分布式锁(一)

作者:zarmnosaj
  • 2022-10-17
    四川
  • 本文字数:618 字

    阅读完需:约 1 分钟

使用 SETNX + EXPIRE 实现分布式锁

首先线程在争夺锁的时候,使用 redis 的 setnx 命令,因为 redis 是单线程, 能保证 setnx 同一个 key 时,可以成功执行的命令只有一个,也就是说,只有一个线程能获取锁,其他线程在执行 setnx 失败后,即陷入阻塞状态,或者自旋等待。


当抢到锁,线程执行逻辑,执行完之后删除 key,进行锁释放,其他锁可恢复就绪状态,准备再执行 setnx 命令争抢锁。在此之下,当持有锁的线程发生了异常,或者宕机,就会造成锁无法释放的情况,此时其他线程就会永远无法得到锁。为了避免这种情况的发生,在 setnx key 时,同时指定一个过期时间,比如设置 10s,就算此时线程发生异常无法释放锁,在 10s 之后,key 会过期,锁就会自动释放。


setnx 说明:线程在执行 SETNX 时, 如果此时 key 不存在,则 SETNX 成功会返回 1,如果这个 key 已经存在,则会返回 0。

SETNX + 时间

在 setnx + expire 方案中,setnx 和 expire 两个命令分开执行了,不是原子操作。非原子操作,那两个命令执行的间隔,必然会可能发生其他的事,比如如果执行完 setnx,还没执行 expire 设置过期时间时,进程中断或者服务宕机,那么这个锁也会出现无法释放的情况,其他线程也就永远获取不到锁了。


此时 SETNX + 时间的方式,就可以将 setnx+expire 命令合并,形成原子操作,可以达到相同的效果。


形成原子操作后,也就避免了在两条期间的间隔期间发生其他的事。


这个时间,可以是指定系统时间,也可以指定过期时间,但此时会要求在多服务高可用部署下,每个服务器的系统时间要求是同步的。

发布于: 刚刚阅读数: 4
用户头像

zarmnosaj

关注

靡不有初,鲜克有终 2020-02-06 加入

成都后端混子

评论

发布
暂无评论
redis实现分布式锁(一)_10月月更_zarmnosaj_InfoQ写作社区