IT袋

当前位置:主页 > 经验教程 > 建站编程 >

SpringBoot

SpringBoot Redis分布式锁的正确实现方式

时间:2024-01-24 18:50:11 来源:IT袋 作者:马勇
导读:SpringBoot,对于大多数网友来说SpringBoot的相关介绍,如有不对的地方欢迎指正! 在说分布式锁之前,我们先说下为什么需要分布式锁。 在单机部署的时候,我们可以使用Java中提供

SpringBoot

对于大多数网友来说SpringBoot的相关介绍,如有不对的地方欢迎指正!

在说分布式锁之前,我们先说下为什么需要分布式锁。

在单机部署的时候,我们可以使用Java中提供的JUC锁机制避免多线程同时操作一个共享变量产生的安全问题。JUC 锁机制只能保证同一个 JVM 进程中的同一时刻只有一个线程操作共享资源。

一个应用部署多个节点,多个进程如果要修改同一个共享资源,为了避免操作乱序导致的并发安全问题,这个时候就需要引入分布式锁,分布式锁就是用来控制同一时刻,只有一个 JVM 进程中的一个线程可以访问被保护的资源。

分布式锁很重要,然而很多公司的系统可能还在跑着有缺陷的分布式锁方案,其中不乏一些大型公司。

所以,不念今天分享一个正确 Redis 分布式锁代码实战,让你一飞冲天,该代码可直接用于生产,不是简单的 demo。

SpringBoot

温馨提示:如果你只想看代码实战部分,可直接翻到 SpringBoot 实战章节。

错误的分布式锁

说正确方案之前,先来一个错误的,知道错在哪,才能意识到如何写正确。

在银行工作的小白老师,使用 Redis SET 指令实现加锁, 指令满足了当 key 不存在则设置 value,同时设置超时时间,并且满足原子语意。

SET lockKey 1 NX PX expireTime
  • lockKey表示锁的资源,value 设置成 1。
  • NX:表示只有lockKey不存在的时候才能SET成功,从而保证只有一个客户端可以获得锁。
  • PX expireTime设置锁的超时时间,单位是毫秒;也可以使用EX seconds以秒为单位设置超时时间。

至于解锁操作,小白老师果决的使用 DEL指令删除。一个分布式锁方案出来了,一气呵成,组员不明觉厉,纷纷竖起大拇指,伪代码如下。

//加锁成功
if(jedis.set(lockKey, 1, "NX", "EX", 10) == 1){
  try {
      do work //执行业务
  } finally {
    //释放锁
     jedis.del(key);
  }
}

然而,这是一个错误的分布式锁。问题在于解锁的操作有可能出现释放别人的锁的情况。

有可能出现释放别人的锁的情况。

  1. 客户端 A 获取锁成功,设置超时时间 10 秒。
  2. 客户端 A 执行业务逻辑,但是因为某些原因(网络问题、FullGC、代码垃圾性能差)执行很慢,时间超过 10 秒,锁因为超时自动释放了。
  3. 客户端 B 加锁成功。
  4. 客户端 A 执行DEL释放锁,相当于把客户端 B 的锁释放了。

相关阅读

  • b2b推广网站有哪些 垂直b2b电商平台推荐

    b2b推广网站有哪些 垂直b2b电商平台推荐

    跟大家聊一聊b2b推广网站有哪些和垂直b2b电商平台推荐方面的内容,下面小编为您详细解答 最近,很多小伙伴都反馈给我。我想知道哪些B2B网站在市场上做得很好。以下是IT袋网小编收集的全

  • 前端开发工程师是做什么的 web前端的工作内容

    前端开发工程师是做什么的 web前端的工作内容

    IT袋网为大家说一说前端开发工程师是做什么的和web前端的工作内容方面的讲解,请看下面详细的介绍。 随着Internet的发展和多个终端的普及,前端开发工程师逐渐受到欢迎,但是前端开发工程

  • 什么是Ceph 有什么特点?

    什么是Ceph 有什么特点?

    如果想了解什么是CephIT技巧方面的经验,相关内容具体如下: 概述 Ceph是当前非常流行的开源分布式存储系统,具有高扩展性、高性能、高可靠性等优点,同时提供 块存储服务 (rbd)、 对象存储

  • [网络工程师]-网络规划与设计-通信规范分析

    [网络工程师]-网络规划与设计-通信规范分析

    相对于大多数人[网络工程师]-网络规划与设计-通信规范分析方面的介绍,下面为详细的介绍。 在网络分析和设计过程中,通信规范分析处于第二个阶段,通过分析网络通信流量和通信模式,发