redission unlock挂起导致获取锁无限等待

概述

现象

Redisson分布式锁报错:attempt to unlock lock, not locked by current thread by node id
java.lang.IllegalMonitorStateException: attempt to unlock lock, not locked by current thread by node id: 193fa0a4-1df0-445f-8737-18b7bb464f64 thread-id: 80

redisson version:3.12.5
redis version:5.0.7
redis cluster mode: 3 master 3 slave deployed in vm
question descript:
In my production environment, a thread(dubheTaskExecutor-pool-2-thread-836) hangs up forever whe invokes RedissonLock.unlock() . And I never found any error in my application log. I am desired to find out if is a bug in redisson 3.12.5.The thread dump file is below(core part) :

"dubheTaskExecutor-pool-2-thread-836" #12180 prio=5 os_prio=0 tid=0x00007f9bc003b000 nid=0x38a6 in Object.wait() [0x00007f9c660de000]
java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
at java.lang.Object.wait(Object.java:502)
at io.netty.util.concurrent.DefaultPromise.await(DefaultPromise.java:252)
- locked <0x00000006a4b32a10> (a io.netty.util.concurrent.ImmediateEventExecutor$ImmediatePromise)
at org.redisson.misc.RedissonPromise.await(RedissonPromise.java:110)
at org.redisson.misc.RedissonPromise.await(RedissonPromise.java:35)
at org.redisson.command.CommandAsyncService.get(CommandAsyncService.java:139)
at org.redisson.RedissonObject.get(RedissonObject.java:90)
at org.redisson.RedissonLock.unlock(RedissonLock.java:477)
at com.sf.beic.common.autoconfig.redisson.DistributedLockerImpl.unlock(DistributedLockerImpl.java:57)
at com.sf.beic.common.autoconfig.redisson.RedissonDistributedLockerUtil.unlock(RedissonDistributedLockerUtil.java:37)
at com.sf.dubhe.pay.gateway.task.ThirdTransferQueryTask$1.run(ThirdTransferQueryTask.java:162)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at java.lang.Thread.run(Thread.java:748)

解决方案

lock.isLocked():判断要解锁的key是否已被锁定。
lock.isHeldByCurrentThread():判断要解锁的key是否被当前线程持有。

public void unlockSingle(String lockKey, String user) {
RLock lock = redissonClient.getLock(lockKey);
if (lock.isLocked() && lock.isHeldByCurrentThread()) {
		lock.unlock();
	}
}

参考

Redisson分布式锁报错:attempt to unlock lock, not locked by current thread by node idl
Redisson 3.12.5 unlock hang forever #3393
使用redisson遇到的坑

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
循环获取释放Redisson是为了实现超时续约的机制。当一个线程获取后开始执行业务逻辑,但由于业务执行时出现卡顿,导致超时后被释放。此时,如果业务逻辑还未执行完毕,其他线程可能会获取到分布式并开始执行,从而引发线程安全问题。为了避免这种情况,需要循环获取并续约,直到业务逻辑执行完毕后释放。 在Redisson中,可以使用`tryLock()`方法来尝试获取,如果获取成功,则可以执行业务逻辑。在业务逻辑执行完毕后,需要调用`unlock()`方法来释放。如果获取失败,则可以根据需要进行相应的处理。 在给定的代码示例中,`method1()`和`method2()`分别代表两个不同的方法,它们都尝试获取并执行业务逻辑。如果获取失败,则会输出相应的错误信息。在`finally`块中,会调用`unlock()`方法来释放。 需要注意的是,循环获取释放Redisson的具体实现可能会根据业务需求和代码逻辑而有所不同。以上提供的代码示例仅供参考。 #### 引用[.reference_title] - *1* *3* [《Redis实战篇》五、分布式-redission](https://blog.csdn.net/LXYDSF/article/details/128439761)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^insertT0,239^v3^insert_chatgpt"}} ] [.reference_item] - *2* [模拟Redisson获取 释放 续命](https://blog.csdn.net/xiaoshitou_2015/article/details/129987957)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v91^insertT0,239^v3^insert_chatgpt"}} ] [.reference_item] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

融极

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值