redis的分布式锁

分布式锁是一种用在分布式系统中实现同步和互斥访问的机制。

1、分布式锁概念

满足分布式系统或者集群模式下,多进程可见 并且互斥的锁。

分布式锁的核心思想就是让分布式集群中的节点都适用同一把锁,只要大家使用的是同一把锁,就能锁住线程,让程序串行执行。

分布式锁需要满足的条件:

  1. 可见性:多个线程都能看到相同的结果 --- > 不是并发编程中的内存可见性,而是多个进程之间能够互相感知变化
  2. 互斥:分布式锁的基本条件,是程序串行执行
  3. 高可用
  4. 高性能
  5. 安全性

常见的分布式锁:

  1. mysql:mysql本身就带有锁机制,但是因为性能一般,所有不常用做分布式锁
  2. redis:利用setnx这种互斥命令就可以简单实现分布式锁
  3. zookeeper:利用节点的唯一性和有序性实现互斥。
2、redis实现分布式锁的核心思路

利用redis的set nx 方法,多个线程进入时,只有第一个线程能够 setnx key 成功,成功则说明他抢到了锁,那么就可以继续执行业务,执行完毕删除锁,没有成功的则等待一定时间重试。

使用set nx 加锁的时候,一定要注意加上过期时间,否则,一旦获得锁的进程宕机,那么锁就永远无法释放,其他进程也就没办法获取锁了。

3、业务处理时间较长会出现什么情况?

场景:

  1. 线程1获取锁,然后处理业务,但是因为业务处理时间较长,直到锁过期了还没处理完,此时线程2获取到了锁,然后处理线程2的业务
  2. 一段时间后,线程1处理完了,处理释放锁的逻辑,但是此时是线程2持有锁,他就把线程2的锁给释放了 --- 这就会产生问题

解决方法:

  1. 加长锁的过期时间,并添加一个子线程,每10s去确认当前持有锁的线程是否在线,如果在线,就将过期时间重设延长
  2. 给锁加一个唯一的UUID,保证每把锁的key是和自己的进程是绑定的

我们开发中,可以直接用Redisson来解决上述的问题,我们常说的watch dog就是上述所说的确认当前线程是否存活的子线程。

4、如果redis采用的是主从集群模式,会有什么样的问题?

因为redis采用的是AP模式,也就是保证高可用和高性能,而不是去保证高一致性,加锁时只会往master节点设置锁,并直接返回结果(此时如果master节点掉线,锁还没有同步给slave节点,而redis的选举机制会重新推选一个新的master,但是这个新的master没有同步到刚刚加的锁,此时就会发送线程不安全问题)

Redisson的解决方案: RedLock

RedLock的逻辑是,需要把锁加锁的逻辑同步到集群中的所有节点上(master和slave),如果大多数的redis节点(>n/2+1)成功获取到了锁,并且获取锁的总消耗时间没有超过锁的有效时间,才会被认为成功获取锁,否则认为获取锁失败,如果获取锁失败了,那么客户端应该立即向所有的redis节点发起释放锁的操作,用LUA脚本。

相关推荐
薛定谔的算法2 小时前
phoneGPT:构建专业领域的检索增强型智能问答系统
前端·数据库·后端
Databend3 小时前
Databend 亮相 RustChinaConf 2025,分享基于 Rust 构建商业化数仓平台的探索
数据库
得物技术4 小时前
破解gh-ost变更导致MySQL表膨胀之谜|得物技术
数据库·后端·mysql
Raymond运维9 小时前
MariaDB源码编译安装(二)
运维·数据库·mariadb
沢田纲吉9 小时前
🗄️ MySQL 表操作全面指南
数据库·后端·mysql
Seven9710 小时前
剑指offer-31、整数中1出现的次数
redis
RestCloud1 天前
SQL Server到Hive:批处理ETL性能提升30%的实战经验
数据库·api
RestCloud1 天前
为什么说零代码 ETL 是未来趋势?
数据库·api
ClouGence1 天前
CloudCanal + Paimon + SelectDB 从 0 到 1 构建实时湖仓
数据库
努力的小郑1 天前
从一次分表实践谈起:我们真的需要复杂的分布式ID吗?
分布式·后端·面试