Redis分布式锁导致死锁、锁误删的场景及解决方法
创作时间:
作者:
@小白创作中心
Redis分布式锁导致死锁、锁误删的场景及解决方法
引用
CSDN
1.
https://blog.csdn.net/qq_33204709/article/details/139338591
Redis 天生就可以作为一个分布式系统来使用,所以它实现的锁都是分布式锁。
Redis 可以通过 setnx 命令(set if not exists)命令实现分布式锁,实现方式如下所示:
# 加锁
setnx mylock 1
# 释放锁
del mylock
通过执行结果是否为1,可以判断是否成功获取到锁,如下图所示:
Redis 分布式锁存在什么问题?
Redis 分布式锁存在两个问题:
死锁问题:如果在加锁之后,未设置过期时间、锁忘记释放、加锁后还没来得及释放锁就宕机了这3种情况都会导致死锁问题。
锁误删问题:设置了超时时间,但是线程执行超过过期时间后锁误删问题。
解决死锁问题
- 方式一:set 升级
MySQL 中解决死锁问题是通过设置超时时间,Redis 也是如此,但是问题来了,第一步先加锁,然后再设置超时时间,那么就不满足原子性了,那怎么办?
官方在 Redis 2.6.12 版本之后,新增了一个功能,我们可以使用一条命令既执行加锁操作,又设置过期时间,相当于:setnx + expire。如下图所示:
- 第1条命令加锁成功,并设置 30s 过期时间。
- 第2条命令跟在第1条命令后,还没有超过 30s,所以加锁失败。
- 方式二:setIfAbsent 新方法
setIfAbsent() 是 Redis 专门为分布式锁实现的原子操作,其中封装了获取 key、设置 key、设置过期时间等操作。
RedisUtils 工具类:
@Component
public class RedisUtils {
@Autowired
private RedisTemplate<String, Object> redisTemplate;
/**
* 原子性操作 加锁
*/
public boolean setIfAbsent(String key, String value, long timeout, TimeUnit unit) {
return Boolean.TRUE.equals(redisTemplate.opsForValue().setIfAbsent(key, value, timeout, unit)
热门推荐
辐条轮怎样精准调整?调整辐条轮时有哪些要点?
卧龙吟2诸葛亮技能阵容兵种搭配推荐攻略
李邦良主任深度解析肺肿瘤防治:中医视角下的全程管理方案
农村地皮买卖合同有效吗?一文详解三种地皮买卖规定
批量视频是怎么生产的软件
不到半年,Figure AI发布第二代人形机器人,称为“地表最先进AI硬件”
春季高发荨麻疹,如何摆脱困扰?
脑干出血:生命中枢的紧急警报
抱怨背后,藏着你未曾察觉的心理真相
沅江芦笋与普通芦笋:两种食材的全面对比
考古重庆⑨ | 奉节县白帝城——延续两千年的军事重镇
耳朵下方与脸颊交界处有鼓包怎么办?可能病因及检查方法全解析
高智商者的七大特征:心机与手腕的艺术
聪明人的这10个特征,你拥有几个?
跨文化冲突的解决策略与实践分享
高敏感是天生的
二次元角色扮演(Cosplay)高手必备独特穿搭技巧全攻略
DIY创意:将废弃篮子变身挂篮花盆
股东如何影响企业投资 股东的投入对资产的影响
如何分析高楼在地震中的受力情况?这种受力情况如何影响建筑结构?
C语言中使用两个while循环的方法详解
什麼時候去日本關西騎自行車?最佳季節指南
标准投资回收期详解:项目管理中的关键指标,如何计算?
冷知识!为什么吃冰淇淋会突然头痛一下?
实木家具避坑指南:从材质到售后,这6大雷区千万别踩!
Android系统流畅性揭秘:硬件 vs 软件,版本更新关键
探究农历丁卯年背后的文化与历史意义
摩托车头盔选购全攻略:从材质到安全,一文读懂如何挑选
二手车买卖协议应包含哪些关键条款?这些条款如何保障双方权益?
【盘点】膝痛不同位置,代表着的疾病