Redis 中如何实现分布式锁?

Redis实现分布式锁(面试结构化回答)

核心原理

利用Redis单线程执行命令、原子性,多个客户端抢占同一个key,抢到key代表获取锁;释放key代表释放锁,以此实现多进程/多机器互斥访问共享资源。

1. 获取锁

错误写法

redis 复制代码
SET lock 1
EXPIRE lock 30

两条命令非原子,如果执行完set之后服务宕机,没有设置过期时间,锁会永久死锁。

正确命令(原子操作)

redis 复制代码
SET lock_key unique_value NX EX 30
  • NX:key不存在才设置,保证互斥;
  • EX 30:锁自动过期时间,防止宕机死锁;
  • unique_value:客户端生成唯一标识(UUID/线程ID),用来区分锁是谁加的,不能随便释放别人的锁。

2. 释放锁

重点:不能直接DEL lock_key,会把别的线程持有的锁删掉。

错误:直接del

如果业务执行慢,锁过期自动释放,别的线程拿到锁,此时当前线程执行del,直接删掉别人的锁。

正确:Lua脚本原子释放

lua 复制代码
-- 判断是自己加的锁,才删除
if redis.call('get',KEYS[1]) == ARGV[1] then
    return redis.call('del',KEYS[1])
else
    return 0
end

Lua脚本保证判断+删除是一条原子操作。

3. 锁续期(看门狗机制 watchdog)

  • 场景:业务还没执行完,锁快过期了,锁被自动释放,出现并发问题。
  • 实现:客户端开启后台线程,检测锁快要过期,如果线程还持有锁,自动延长过期时间。
  • Redisson已经封装好看门狗,不需要自己手写。

4. 单机Redis分布式锁存在的问题

  1. 主从异步复制问题:客户端在master拿到锁,锁还没同步到slave,master宕机,slave升级为主,锁丢失,出现锁失效。
  2. 解决方案:Redlock红锁,需要多台独立Redis节点,半数以上节点加锁成功才算拿到锁;运维成本高,实际线上很少用。
  3. 工业更常用:Zookeeper分布式锁 / 数据库乐观锁做兜底。

5. 实际开发建议

尽量直接使用Redisson,不要手写Redis分布式锁。

Redisson已经封装:

  • 原子加锁释放
  • 看门狗自动续期
  • 可重入锁
  • 锁等待、重试机制

总结

  1. 加锁用SET key value NX EX原子命令,设置唯一value;
  2. 释放锁必须Lua脚本校验归属,不能直接del;
  3. 业务超时要看门狗续期,避免锁提前过期;
  4. 单机主从切换会丢锁,Redlock理论解决,工程优先用Redisson。

追问记忆点:原子加锁、唯一标识、Lua释放、看门狗续期、主从丢失锁风险。

相关推荐
李兆龙的博客2 小时前
问津集 #26:Lakebase——Postgres 的版本化页面存储、数据库分支与计算弹性
数据库
倔强的石头_4 小时前
聊聊金仓KFS:一款把数据同步软件做扎实的产品
数据库
闲云野鹤在人间5 小时前
MySQL|从理论、安装、备份到主从复制、MHA高可用详解
linux·运维·数据库·mysql·云计算
禾小西5 小时前
Redis:从两大维度和三大主线建立知识体系
数据库·redis·缓存
禾小西5 小时前
Redis 数据结构:快速的 Redis 有哪些慢操作?
数据结构·数据库·redis
数据库小学妹6 小时前
数据共享交换平台选型:交换方式对比与避坑指南
数据库·信创·数据同步·数据交换平台·政务数据共享·数据共享交换平台·数据库底座
loong_XL7 小时前
决策模型做内容安全检测:从踩坑到上线
数据库·安全·jev·决策模型
这个DBA有点耶7 小时前
数据库双轨并行实战:全量并行策略、增量延迟控制、双向回切与一致性校验
数据库·架构·dba
adinnet20268 小时前
保单、赔付与渠道问数:保险经营数据如何实现按需查询
大数据·数据库·人工智能
云贝贝贝8 小时前
PostgreSQL 分区表:从设计到运维,大表不再卡
运维·数据库·postgresql