当前位置: 首页 > news >正文

如何实现分布式锁

一、锁的作用

锁是为了解决多线程情况下,对于共享资源的访问安全问题。
但是当系统是分布式的时候,本地锁已经没法锁住所需要的资源,因为本地获取了锁,其他系统无法得知本地锁的情况。
分布式锁,是独立于系统的第一方实现的功能。因而状态可供不同系统获取。

二、分布式锁实现

2.1、基于redis实现

基于redis实现的分布式锁是当下比较流行的一种实现方式。
利用redis的set命令,用全路径类名方法名作为key,当前线程id作为value,插入一条记录,当且仅当该记录不存在。
如果返回1,代表成功获取到锁,返回0代表锁已经被其他线程获取了。
命令 格式:set key value nx ex 过期时间
释放锁的时候需要判断是否是自己加的锁,只能释放自己加的锁。

这样即可以防止系统挂掉导致无法释放锁的情况。不过又引入了锁内代码还没执行完就提前释放的情况,因此需要锁续期。可以设置一个守护线程,在快要到达第一次超时时间的时候启动守护线程,给锁续期,每隔所续的时间,再次启动守护线程续期。

2.2、基于数据库实现

利用数据库唯一索引来实现分布式锁。
建立一个分布式锁表,包含字段全路径类名、方法名,给全路径类名+方法名建立唯一索引。唯一索引会限制只有一个线程能成功插入数据。
获取锁的时候,就往数据库插入一条数据,如果插入成功,则代表获取到分布式锁。
释放锁的时候就删除该记录。

存在的问题:如果获取锁之后,数据库或者服务器挂了,那么分布式锁就没法释放。使用主从数据库可以解决数据库挂了的问题。服务器挂了的问题可以通过启动一个定时任务,根据记录创建时间,定时删除数据库超时的记录。

可以通过记录获取锁的主机信息和线程信息,如果查到已存在的记录属于当前线程,就将锁分配给他,实现可重入。

2.3、基于数据库排他锁实现

在查询语句的后面加上for update,数据库会启动排他锁,利用排他锁可以实现分布式锁。
用户查询到数据就代表他获取了锁,可以执行业务代码,最后commit提交释放排他锁。
数据库被加了排他锁之后,其他线程还想加排他锁就会被阻塞。

http://www.lryc.cn/news/42271.html

相关文章:

  • 使用VS2019连接Microsoft SQL Server Compact 4.0数据库
  • Vue2 和 Vue3 的对比
  • [数据结构]二叉树的链式存储结构
  • 黑马程序员 Redis 踩坑及解决
  • Matlab实现粒子群算法
  • tailwindcss 写原生html
  • Java开发一年不到,来面试居然敢开口要20K,面完连8K都不想给~
  • LeetCode题解 20(17,79) 电话号码的字母组合,单词搜索<回溯>
  • 路径之谜 蓝桥杯 89
  • Mysql数据库如何调优
  • CAN(FD)记录仪在新能源汽车整车控制器(VCU)、电池管理系统(BMS)、电机控制器(MCU)、发动机ECU中的应用,免去出差烦恼
  • 【设计模式】23种设计模式之七大原则
  • python - 文件操作
  • docker打包golang应用
  • redis 内容总结
  • 贪心算法(一)
  • 【栈和队列OJ题】有效的括号用队列实现栈用栈实现队列设计循环队列
  • kuernetes 资源对象分析报错
  • 动态内存的开辟
  • 【蓝桥杯-筑基篇】搜索
  • week5-质数-最大公约数-快速幂-组合计数-博弈论
  • CloudCompare 二次开发(6)——插件中拖拽添加Qt窗口(区域生长算法为例)
  • 2023值得推荐的高颜值Vue3.0 Web PC端UI框架,赶紧收藏学习!
  • Springboot项目Aop、拦截器、过滤器横向对比
  • 为了之后找工作不被虐,每天刷3道《剑指offer》Day-1
  • Linux-磁盘管理介绍
  • 爬虫架构(一):爬虫中的去重处理
  • 算法刷题总结 (二) 回溯与深广搜算法
  • Linux 总结9个最危险的命令,一定要牢记在心!
  • spring cloud