当前位置:网站首页>Implementation of redis distributed lock
Implementation of redis distributed lock
2022-08-04 08:15:00 【Zero shear】
I. Introduction
When we modify the existing data in the system, we need to read it first, and then modify and save it. At this time, it is easy to encounter concurrency problems.Since modification and saving are not atomic operations, some operations on data may be lost in concurrent scenarios.In a single-server system, we often use local locks to avoid problems caused by concurrency. However, when services are deployed in a cluster, local locks cannot take effect between multiple servers. At this time, distributed locks are required to ensure data consistency.accomplish.
Second, the mainstream implementation scheme of distributed locks
Distributed lock based on database
Cache based (Redis, etc.)
Based on Zookeeper
Each distributed lock solution has its own advantages and disadvantages:
Performance: redis is the highest
Reliability: zookeeper highest
3. Implementing distributed locks based on redis
Redis locks mainly use Redis's setnx command
- Locking command: SETNX key value, when the key does not exist, set the key and return success, otherwise return failure.KEY is the unique identifier of the lock, which is generally named according to the business.
- Unlock command: DEL key, releases the lock by deleting the key-value pair, so that other threads can acquire the lock through the SETNX command.
- Lock timeout: EXPIRE key second, set the timeout time of the key to ensure that even if the lock is not explicitly released, the lock can be automatically released after a certain period of time to avoid the resource being locked forever.
There are some problems with the above lock implementation:
1-SETNX-and-EXPIRE-non-atomic
If SETNX is successful, after setting the lock timeout time, the server hangs up, restarts or has network problems, etc., resulting in the EXPIRE command not being executed, and the lock becoming deadlock if the lock timeout time is not set.
Solution:
1. Use Lua script to compose SETNX and EXPIRE into atomic operation
2. Use set key value ex second nx
2, lock removal
If thread A successfully acquires the lock and sets an expiration time of 30 seconds, but the execution time of thread A exceeds 30 seconds, the lock is automatically released after expiration, and thread B acquires the lock at this time; then the execution of A is completed, and thread A usesDEL command to release the lock, but the lock added by thread B has not been executed yet, and the lock added by thread B is actually released by thread A.
Solution:
When set acquires the lock, set a specified unique value (for example: uuid), and acquire this before releasingvalue, determine whether it is your own lock, and if so, release the lock
3. Timeout unlocking leads to concurrency (similar to the previous problem)
If thread A successfully acquires the lock and sets the expiration time to 30 seconds, but the execution time of thread A exceeds 30 seconds, the lock expires and is automatically released. At this time, thread B acquires the lock, and thread A and thread B execute concurrently.
Concurrency of two threads A and B is obviously not allowed. Generally, there are two ways to solve this problem:
- Set the expiration time long enough to ensure that the code logic can complete before the lock is released.
- Add a daemon thread for the thread that acquires the lock, and increase the valid time for the lock that will expire but not be released.
4. The deletion operation lacks atomicity
If thread A successfully acquires the lock and sets the expiration time to 30 seconds, but the execution time of thread A is exactly 30 seconds, the lock is automatically released when it expires. At this time, A just completes the business logic and makes a judgment to release the lock.But before the lock is released, thread B acquires the lock again, and then thread A uses the DEL command to release the lock, but the lock added by thread B has not been executed yet, and the lock added by thread B actually released by thread A.
Solution:
Use Lua scripts to ensure atomicity of locking and releasing locks.
5. How does Lua script ensure its atomicity
Redis embeds a lua environment (very small) to run lua scripts. When running lua scripts, other steps and commands will not be run. It is similar to adding locks to the code executing lua scripts, so its atomicity is guaranteed..
Four. Summary
To ensure that distributed locks are available, we at least make sureThe implementation of the lock also satisfies the following four conditions:
- Mutually exclusive.At any time, only one client can hold the lock.
- No deadlock occurs.Even if a client crashes while holding the lock and does not actively unlock it, it is guaranteed that other clients can lock in the future.
- The ringer must also be tied to the bell.Locking and unlocking must be done by the same client, and the client cannot unlock the locks added by others.
- Locking and unlocking must be atomic.
边栏推荐
- 解决:Hbuilder工具点击发行打包,一直报尚未完成社区身份验证,请点击链接xxxxx,项目xxx发布H5失败的错误。
- The sorting algorithm including selection, bubble, and insertion
- 研究性学习专题 3_LL(1)语法分析设计原理与实现
- inject() can only be used inside setup() or functional components.
- 高等代数_证明_两个矩阵乘积为0,则两个矩阵的秩之和小于等于n
- [Computer recording screen] How to use bandicam to record the game setting graphic tutorial
- Interpretation of new features | MySQL 8.0 online adjustment REDO
- 通过GBase 8c Platform安装数据库集群时报错
- 【我想要老婆】
- MySQL BIGINT 数据类型
猜你喜欢
[Computer recording screen] How to use bandicam to record the game setting graphic tutorial
Typora_Markdown_图片标题(题注)
IntelliJ新建一个类或者包的快捷键是什么?
【电脑录制屏】如何使用bandicam录游戏 设置图文教程
[STM32] STM32F103 series name and package, memory
inject() can only be used inside setup() or functional components.
【CNN基础】转置卷积学习笔记
此时已莺飞草长,愿世间美好与你环环相扣
线程安全问题
2022的七夕,奉上7个精美的表白代码,同时教大家改源码快速自用
随机推荐
【NOI模拟赛】纸老虎博弈(博弈论SG函数,长链剖分)
Distributed Computing Experiment 4 Random Signal Analysis System
并查集介绍和基于并查集解决问题——LeetCode 952 按公因数计算最大组件大小
【JS 逆向百例】某网站加速乐 Cookie 混淆逆向详解
预测性维护学习之路
unity3d-Animation&&Animator接口(基本使用)
inject() can only be used inside setup() or functional components.
binder通信实现
尚医通【预约挂号系统】总结
leetcode 22.8.1 二进制加法
redis stream 实现消息队列
微信消息从发送到接收,经历了什么?如何防止丢包
MYSQL JDBC图书管理系统
Distributed Computing Experiment 2 Thread Pool
使用腾讯云发送短信 ---- 手把手教你搞定所有步骤
Interpretation of new features | MySQL 8.0 online adjustment REDO
关于常用状态码4XX提示错误
LeetCode 135. 分发糖果
实现加载驱动、得到数据库对象、关闭资源的代码复用,将代码提取到相应的工具包里边。优化程序
【电脑录制屏】如何使用bandicam录游戏 设置图文教程