Redisson 框架详解
目录
一.为什么要使用分布式锁?
二.Redisson 的基本使用:
1.添加 Redisson 依赖:
2.在 application.yml 配置 Redis:
3. 创建 Redisson 客户端:
(1)单节点模式:
(2)集群模式:
4.注入RedissonClient:
5.使用 Redisson 存储和获取值:
三.配置集群连接池:
1. Redisson 集群连接池配置项:
2. 配置 Redis 集群的连接池:
四.如何在Boot项目中使用Redission实现分布式锁?
1.引入 Redisson 依赖:
2.配置 Redisson:
3.在 Spring Boot 中注入 RedissonClient:
4.使用分布式锁:
Redisson 是一个基于 Redis 的高效 Java 客户端,封装了 Redis 的大部分功能,提供了更为丰富和高效的操作接口,能够帮助开发者更便捷地进行分布式缓存、分布式锁、分布式集合等操作。它不仅支持 Redis 的基本操作,还提供了更多的高级功能,如分布式锁、分布式集合、分布式计数器等,可以大大简化分布式应用的开发。
一.为什么要使用分布式锁?
分布式锁是解决 分布式系统中的资源竞争问题 的一种有效机制。在高并发分布式系统中,多个服务节点可能同时访问同一资源(如数据库、文件系统等)。这种竞争可能导致数据的不一致性、重复操作、死锁等问题,因此,使用分布式锁来保证同一时刻只有一个节点能够访问共享资源,从而确保系统的正确性和稳定性。
在单机系统中,当多个线程访问共享资源时,操作系统通常使用互斥锁(如 Java 中的 synchronized 或 ReentrantLock)来保证同一时刻只有一个线程能访问该资源。而在分布式系统中,资源通常分布在多个服务实例或节点上,单纯的本地锁(如 synchronized)无法跨节点进行协调,因此需要分布式锁来确保不同节点间的同步。
使用分布式锁的方式:
- 所有节点都尝试获取锁,如果一个节点获得了锁,它将执行任务。
- 其他节点则会等待或者跳过执行该任务,避免重复执行。
使用场景:
- 防止多次执行相同的任务
- 确保分布式系统中资源的独占访问
- 控制并发数量
二.Redisson 的基本使用:
1.添加 Redisson 依赖:
在项目中使用 Redisson,首先需要添加 Redisson 的 Maven 依赖:
<dependency><groupId>org.redisson</groupId><artifactId>redisson</artifactId><version>3.16.1</version> <!-- 请根据最新版本替换 -->
</dependency>
2.在 application.yml 配置 Redis:
# 单节点
redisson:address: redis://127.0.0.1:6379
# 集群
redisson:cluster:addresses: - redis://127.0.0.1:7000- redis://127.0.0.1:7001- redis://127.0.0.1:7002
3. 创建 Redisson 客户端:
Redisson 提供了两种方式来创建客户端:单节点模式 和 集群模式。
(1)单节点模式:
在单节点模式下,我们只需要连接到一个 Redis 实例,在配置类中:
import org.redisson.api.RedissonClient;
import org.redisson.config.Config;
import org.redisson.config.SingleServerConfig;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.redisson.Redisson;@Configuration
public class RedissonConfig {@Beanpublic RedissonClient redissonClient() {// 配置单节点 RedisConfig config = new Config();SingleServerConfig serverConfig = config.useSingleServer();serverConfig.setAddress("redis://127.0.0.1:6379");serverConfig.setPassword("yourpassword");return Redisson.create(config);}
}
(2)集群模式:
import org.redisson.api.RedissonClient;
import org.redisson.config.Config;
import org.redisson.config.ClusterServersConfig;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.redisson.Redisson;import java.util.List;@Configuration
public class RedissonClusterConfig {// 从配置文件中读取 Redis 集群的地址@Value("${redisson.cluster.addresses}")private List<String> clusterAddresses;@Beanpublic RedissonClient redissonClient() {// 创建 Redis 配置对象Config config = new Config();// 配置集群ClusterServersConfig clusterConfig = config.useClusterServers();// 添加集群节点地址for (String address : clusterAddresses) {clusterConfig.addNodeAddress(address);}// 如果需要配置密码,使用 setPassword 方法// clusterConfig.setPassword("yourpassword");// 创建并返回 Redisson 客户端return Redisson.create(config);}
}
4.注入RedissonClient:
通过 @Autowired 注入 RedissonClient 到需要使用的服务类中。
import org.redisson.api.RedissonClient;
import org.redisson.api.RMap;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;@Service
public class RedisService {@Autowiredprivate RedissonClient redissonClient;public void demoMapUsage() {// 获取 Redis 集群中的分布式 MapRMap<String, String> map = redissonClient.getMap("myMap");map.put("name", "Alice");map.put("age", "30");System.out.println("Name: " + map.get("name"));System.out.println("Age: " + map.get("age"));}
}
5.使用 Redisson 存储和获取值:
RBucket<String>是 Redisson 提供的一个接口,它代表 Redis 中一个字符串类型的值。我们可以通过它来存储和获取一个键值对。
import org.redisson.api.RBucket;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;@Service
public class RedisService {@Autowiredprivate RedissonClient redissonClient;// 存储值public void setValue(String key, String value) {RBucket<String> bucket = redissonClient.getBucket(key); // 获取 Redis 中的指定 keybucket.set(value); // 存储值}// 获取值public String getValue(String key) {RBucket<String> bucket = redissonClient.getBucket(key); // 获取 Redis 中的指定 keyreturn bucket.get(); // 获取存储的值}
}
三.配置集群连接池:
在使用 Redisson 配置 Redis 集群时,我们可以通过配置连接池来管理连接的数量、连接的超时时间等。Redisson 提供了灵活的配置方式来定制集群模式的连接池。
1. Redisson 集群连接池配置项:
Redisson 提供了多个与连接池相关的配置项,主要包括以下几个:
- masterConnectionPoolSize:主节点连接池的大小(连接数量)。
- slaveConnectionPoolSize:从节点连接池的大小(连接数量)。
- connectionMinimumIdleSize:连接池中保持的最小空闲连接数。
- connectionPoolSize:连接池的最大连接数。
- idleConnectionTimeout:空闲连接的超时时间。
- connectTimeout:连接的超时时间。
- timeout:操作超时时间(请求的最大等待时间)。
2. 配置 Redis 集群的连接池:
在 application.yml 中配置连接池参数:
redisson:cluster:addresses: - redis://127.0.0.1:7000- redis://127.0.0.1:7001- redis://127.0.0.1:7002# 集群连接池配置master-connection-pool-size: 100 # 主节点连接池大小slave-connection-pool-size: 50 # 从节点连接池大小connection-pool-size: 200 # 总连接池大小connection-minimum-idle-size: 10 # 最小空闲连接数idle-connection-timeout: 10000 # 空闲连接超时connect-timeout: 3000 # 连接超时timeout: 5000 # 请求超时
配置连接池是确保 Redis 集群高效运行的关键,它能够有效管理连接的数量,提高 Redis 的性能,避免频繁地创建和销毁连接。
如果我们在
application.yml或application.properties文件中配置了 Redisson 的连接池参数,并且使用了redisson-spring-boot-starter,Spring Boot 会自动读取这些配置并初始化连接池。
四.如何在Boot项目中使用Redission实现分布式锁?
在 Spring Boot 项目中使用 Redisson 实现分布式锁,主要涉及到以下几个步骤:
- 引入 Redisson 依赖
- 配置 Redisson 客户端
- 在 Spring Boot 中注入
RedissonClient- 使用分布式锁
1.引入 Redisson 依赖:
<dependency><groupId>org.redisson</groupId><artifactId>redisson-spring-boot-starter</artifactId><version>3.16.1</version> <!-- 请根据最新版本替换 -->
</dependency>
2.配置 Redisson:
redisson:# Redis 集群配置cluster:# 集群节点地址,多个节点地址用逗号分隔nodes:- redis://127.0.0.1:7000- redis://127.0.0.1:7001- redis://127.0.0.1:7002- redis://127.0.0.1:7003- redis://127.0.0.1:7004- redis://127.0.0.1:7005# Redis 密码(如果有密码的话)password: yourpassword # Redis 的密码# 连接池配置connection-pool-size: 100 # 连接池大小connection-minimum-idle-size: 10 # 最小空闲连接数idle-connection-timeout: 10000 # 空闲连接超时(毫秒)connect-timeout: 3000 # 连接超时(毫秒)timeout: 5000 # 请求超时(毫秒)retries: 3 # 在获取连接时的最大重试次数retry-interval: 1000 # Redis 集群模式下的超时时间wait-timeout: 3000 # 最大等待连接的时间(毫秒)subscription-mode: false # 集群模式下是否启用超时管理threads: 16 # 线程池大小
3.在 Spring Boot 中注入 RedissonClient:
在 Spring Boot 中,我们可以通过 @Autowired 注入 RedissonClient,然后在服务类中使用它进行 Redis 操作。
import org.redisson.api.RLock;
import org.redisson.api.RBucket;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;import java.util.concurrent.TimeUnit;@Service
public class RedisWithLockService {@Autowiredprivate RedissonClient redissonClient;// 锁的名称private static final String LOCK_KEY = "myLock";// 存储到 Redis 中的键private static final String REDIS_KEY = "userBalance";// 分布式锁处理业务逻辑public void updateBalance(String userId, double newBalance) {// 获取分布式锁RLock lock = redissonClient.getLock(LOCK_KEY);try {// 尝试获取锁,最多等待 10 秒,锁自动释放时间为 30 秒if (lock.tryLock(10, 30, TimeUnit.SECONDS)) {// 锁获取成功,执行 Redis 操作System.out.println("Lock acquired, updating balance...");// 获取当前用户的余额double currentBalance = getUserBalanceFromRedis(userId);System.out.println("Current balance: " + currentBalance);// 更新余额(模拟业务逻辑)double updatedBalance = currentBalance + newBalance;System.out.println("Updated balance: " + updatedBalance);// 将新的余额存储回 RedissetUserBalanceToRedis(userId, updatedBalance);} else {System.out.println("Unable to acquire lock for updating balance.");}} catch (InterruptedException e) {e.printStackTrace();} finally {// 确保释放锁if (lock.isHeldByCurrentThread()) {lock.unlock();}}}// 获取用户余额(从 Redis 中)private double getUserBalanceFromRedis(String userId) {RBucket<Double> bucket = redissonClient.getBucket(REDIS_KEY + ":" + userId);return bucket.isExists() ? bucket.get() : 0.0; // 如果值存在则获取,如果没有则返回 0}// 更新用户余额(存入 Redis)private void setUserBalanceToRedis(String userId, double balance) {RBucket<Double> bucket = redissonClient.getBucket(REDIS_KEY + ":" + userId);bucket.set(balance); // 存储新的余额}
}
4.使用分布式锁:
在 RedisLockService 中定义了 processWithDistributedLock 方法,调用时,Redisson 将确保在同一时刻只有一个进程/线程可以进入锁的保护区域。
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;@RestController
public class RedisWithLockController {@Autowiredprivate RedisWithLockService redisWithLockService;// 模拟调用分布式锁更新用户余额的接口@GetMapping("/updateBalance")public String updateBalance(@RequestParam String userId, @RequestParam double amount) {redisWithLockService.updateBalance(userId, amount);return "Balance update request received for user: " + userId;}
}
通过访问下面接口地址:
http://localhost:8080/updateBalance?userId=user1&amount=100
查看后端返回数据。
总结:
- Redisson 提供了丰富的 API 用于存储和获取 Redis 中的值。你可以通过
RBucket等数据结构操作 Redis 中的数据。- 使用 分布式锁 可以确保在多个服务实例之间协调对共享资源(如 Redis 中的数据)的访问。
- Redisson 的分布式锁非常适合用来保护 Redis 中的临界资源,避免高并发访问导致的数据不一致问题。
相关文章:
Redisson 框架详解
目录 一.为什么要使用分布式锁? 二.Redisson 的基本使用: 1.添加 Redisson 依赖: 2.在 application.yml 配置 Redis: 3. 创建 Redisson 客户端: (1)单节点模式: (…...
正确导入MapStruct并避免与Lombok编译冲突的深入分析
正确导入MapStruct并避免与Lombok编译冲突的深入分析 一、MapStruct与Lombok概述 1.1 MapStruct简介 MapStruct是一个代码生成器,它基于约定优于配置的原则,通过注解处理器在编译时自动生成源代码,实现对象之间的属性映射。MapStruct的优势在于减少样板代码,提高开发效率…...
K8S 黑魔法之如何从 Pod 拿到节点的命令行
搞 K8S 运维的时候,偶尔会遇到一个难题,定位到问题出在某个节点上,而由于权限审批,错误配置等等各种原因,没有办法拿到节点的 SSH 权限,无法进入节点命令行进一步排障。 这个时候,就可以用这个…...
【bluedroid】A2dp Source播放流程源码分析(4)
接上集分析:【bluedroid】A2dp Source播放流程源码分析(3)-CSDN博客 蓝牙和AUDIO之间的接口 蓝牙和audio之间的通信是通过socket,管理socket中的文件是UIPC,UIPC管理两条socket。 A2DP_CTRL_PATH /data/misc/bluedroid/.a2dp_ctrl A2DP_DATA_PATH /data/misc/bluedroid…...
计算机网络 (9)数据链路层
前言 计算机网络中的数据链路层(Data Link Layer)是OSI(开放系统互连)参考模型中的第二层,位于物理层和网络层之间。它在物理层提供的服务基础上,负责在相邻节点之间建立、维护和终止链路,确保数…...
kubernetes学习-集群搭建部署(一)
一、开三台虚拟机进行试验(centos7) 1、初始操作 # 关闭防火墙 systemctl stop firewalld systemctl disable firewalld# 关闭selinux sudo sed -i s/enforcing/disabled/ /etc/selinux/config # 永久 setenforce 0 # 临时# 关闭swap sudo swapoff -a # 临时 s…...
docker commit生成的镜像瘦身
1、清除宿主系统的docker资源 docker system prune -a --volumes 2、清理容器内系统的临时文件和缓存 # 删除包管理器缓存 apt-get clean rm -rf /var/lib/apt/lists/* # 删除日志文件 rm -rf /var/log/* # 删除临时文件 rm -rf /tmp/* 3、安装docker squash工具࿰…...
基于Spring Boot的宠物领养系统的设计与实现(代码+数据库+LW)
摘 要 如今社会上各行各业,都在用属于自己专用的软件来进行工作,互联网发展到这个时候,人们已经发现离不开了互联网。互联网的发展,离不开一些新的技术,而新技术的产生往往是为了解决现有问题而产生的。针对于宠物领…...
7.若依参数设置、通知公告、日志管理
参数设置 对系统中的参数进行动态维护。 关闭验证码校验功能 打开页面注册功能 需要修改前端页面代码 通知公告 促进组织内部信息传递 若依只提供了一个半成品,只实现了管理员可以添加通知公告。 日志管理 追踪用户行为和系统运行状况。 登录日志 和操作日志…...
基于FISCO BCOS的电子签署系统
概述 本项目致力于构建一个安全、高效且功能完备的电子签署系统,通过整合区块链技术与传统数据库管理,为用户提供了可靠的电子签署解决方案,有效应对传统电子签署系统的数据安全隐患,满足企业和个人在数字化办公环境下对电子文档…...
RocketMQ(二)RocketMQ实战
文章目录 一、RocketMQ实战1.1 批量消息发送1.2 消息发送队列自选择1.3 事务消息1.4 SpringCloud集成RocketMQ 二、最佳实践2.1 生产者2.1.1 发送消息注意事项2.1.2 消息发送失败处理方式 2.2 消费者2.2.1 消费过程幂等2.2.2 消费打印日志 2.3 Broker 三、相关问题3.1 为什么要…...
Java重要面试名词整理(十三):RocketMQ
文章目录 简述环境搭建分布式集群配置升级高可用集群 RocketMQ的消息模型基本流程消息确认机制广播消息顺序消息机制延迟消息批量消息过滤消息事务消息ACL权限控制机制 调优消费者端进行幂等控制 核心客户端负载均衡Consumer负载均衡 消息持久化设计Dleger集群的文件同步机制 简…...
机器学习之线性回归算法预测数据
机器学习之线性回归算法预测数据 目录 机器学习之线性回归算法预测数据线性回归算法概念理解算法导入线性回归模型参数理解误差项分析 LinearRegression理解参数理解返回值方法基本格式 预测一元线性回归数据问题及理解可视化数据理解数据预测 预测二元线性回归数据问题及理解数…...
Python | 如何在Matplotlib中仅绘制热图的上/下三角形
热图是一种强大的可视化工具,用于以矩阵格式表示数据,其中各个值由颜色表示。它们对于可视化相关矩阵特别有用,其中矩阵的对称性质使得显示上下三角形变得多余。本文将指导您使用Matplotlib(Python中流行的绘图库)仅绘…...
Leetcode经典题20--长度最小的子数组
题目描述 给定一个含有 n 个正整数的数组和一个正整数 target 。 找出该数组中满足其总和大于等于 target 的长度最小的子数组 [numsl, numsl1, ..., numsr-1, numsr] ,并返回其长度。如果不存在符合条件的子数组,返回 0 。 输入输出示例 输入&…...
【计算机视觉】超简单!维纳滤波的经典案例
Hey小伙伴们!今天来给大家分享一个 计算机视觉 中非常经典且实用的技术——维纳滤波(Wiener Filter)。维纳滤波是一种基于最小均方误差准则的滤波方法,广泛应用于图像去噪、模糊恢复等领域。它不仅可以有效去除图像中的噪声&#…...
【closerAI ComfyUI】快速洗图!高效快速的提示词反推节点——cliption,让洗图出图快人一步不爆显存!
添加图片注释,不超过 140 字(可选) 【closerAI ComfyUI】快速洗图!高效快速的提示词反推节点——cliption,让洗图出图快人一步不爆显存! 大家好,我是Jimmy。反推提示词的节点有很多,像Florence2 、Joycaption2、喵手等。都是非常优秀的。但是呢,就是占用设备资源,加…...
AE Dressler CESAR 1312 Generator Model User Manual
AE Dressler CESAR 1312 Generator Model User Manual...
【513. 找树左下角的值 中等】
题目: 给定一个二叉树的 根节点 root,请找出该二叉树的 最底层 最左边 节点的值。 假设二叉树中至少有一个节点。 示例 1: 输入: root [2,1,3] 输出: 1 示例 2: 输入: [1,2,3,4,null,5,6,null,null,7] 输出: 7 提示: 二叉树的节点个数的范围是 …...
网络通信的瑞士军刀:Python socket库全解析
文章目录 网络通信的瑞士军刀:Python socket库全解析背景库介绍安装与重要性简单库函数使用方法场景应用常见Bug及解决方案总结 网络通信的瑞士军刀:Python socket库全解析 背景 在现代编程中,网络通信是不可或缺的一部分。无论是构建客户端…...
Appium+python自动化(十六)- ADB命令
简介 Android 调试桥(adb)是多种用途的工具,该工具可以帮助你你管理设备或模拟器 的状态。 adb ( Android Debug Bridge)是一个通用命令行工具,其允许您与模拟器实例或连接的 Android 设备进行通信。它可为各种设备操作提供便利,如安装和调试…...
【机器视觉】单目测距——运动结构恢复
ps:图是随便找的,为了凑个封面 前言 在前面对光流法进行进一步改进,希望将2D光流推广至3D场景流时,发现2D转3D过程中存在尺度歧义问题,需要补全摄像头拍摄图像中缺失的深度信息,否则解空间不收敛…...
STM32标准库-DMA直接存储器存取
文章目录 一、DMA1.1简介1.2存储器映像1.3DMA框图1.4DMA基本结构1.5DMA请求1.6数据宽度与对齐1.7数据转运DMA1.8ADC扫描模式DMA 二、数据转运DMA2.1接线图2.2代码2.3相关API 一、DMA 1.1简介 DMA(Direct Memory Access)直接存储器存取 DMA可以提供外设…...
对WWDC 2025 Keynote 内容的预测
借助我们以往对苹果公司发展路径的深入研究经验,以及大语言模型的分析能力,我们系统梳理了多年来苹果 WWDC 主题演讲的规律。在 WWDC 2025 即将揭幕之际,我们让 ChatGPT 对今年的 Keynote 内容进行了一个初步预测,聊作存档。等到明…...
NFT模式:数字资产确权与链游经济系统构建
NFT模式:数字资产确权与链游经济系统构建 ——从技术架构到可持续生态的范式革命 一、确权技术革新:构建可信数字资产基石 1. 区块链底层架构的进化 跨链互操作协议:基于LayerZero协议实现以太坊、Solana等公链资产互通,通过零知…...
DeepSeek 技术赋能无人农场协同作业:用 AI 重构农田管理 “神经网”
目录 一、引言二、DeepSeek 技术大揭秘2.1 核心架构解析2.2 关键技术剖析 三、智能农业无人农场协同作业现状3.1 发展现状概述3.2 协同作业模式介绍 四、DeepSeek 的 “农场奇妙游”4.1 数据处理与分析4.2 作物生长监测与预测4.3 病虫害防治4.4 农机协同作业调度 五、实际案例大…...
均衡后的SNRSINR
本文主要摘自参考文献中的前两篇,相关文献中经常会出现MIMO检测后的SINR不过一直没有找到相关数学推到过程,其中文献[1]中给出了相关原理在此仅做记录。 1. 系统模型 复信道模型 n t n_t nt 根发送天线, n r n_r nr 根接收天线的 MIMO 系…...
HDFS分布式存储 zookeeper
hadoop介绍 狭义上hadoop是指apache的一款开源软件 用java语言实现开源框架,允许使用简单的变成模型跨计算机对大型集群进行分布式处理(1.海量的数据存储 2.海量数据的计算)Hadoop核心组件 hdfs(分布式文件存储系统)&a…...
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材)
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材) 这个项目能干嘛? 使用 gemini 2.0 的 api 和 google 其他的 api 来做衍生处理 简化和优化了文生图和图生图的行为(我的最主要) 并且有一些目标检测和切割(我用不到) 视频和 imagefx 因为没 a…...
【JavaSE】多线程基础学习笔记
多线程基础 -线程相关概念 程序(Program) 是为完成特定任务、用某种语言编写的一组指令的集合简单的说:就是我们写的代码 进程 进程是指运行中的程序,比如我们使用QQ,就启动了一个进程,操作系统就会为该进程分配内存…...
