spring boot整合Redis监听数据变化

一、前言

Redis提供了数据变化的通知事件,可以实时监测key和value的变化,客户端可以通过订阅相关的channel来接收这些通知事件,然后做相应的自定义处理,详细的介绍可以参考官方文档Redis keyspace notifications | Docs

使用Redis时,可以在配置文件中管理相应的配置,默认配置是不开启事件通知的。

############################# Event notification ##############################

# Redis can notify Pub/Sub clients about events happening in the key space.
# This feature is documented at http://redis.io/topics/notifications
#
# For instance if keyspace events notification is enabled, and a client
# performs a DEL operation on key "foo" stored in the Database 0, two
# messages will be published via Pub/Sub:
#
# PUBLISH __keyspace@0__:foo del
# PUBLISH __keyevent@0__:del foo
#
# It is possible to select the events that Redis will notify among a set
# of classes. Every class is identified by a single character:
#
#  K     Keyspace events, published with __keyspace@<db>__ prefix.
#  E     Keyevent events, published with __keyevent@<db>__ prefix.
#  g     Generic commands (non-type specific) like DEL, EXPIRE, RENAME, ...
#  $     String commands
#  l     List commands
#  s     Set commands
#  h     Hash commands
#  z     Sorted set commands
#  x     Expired events (events generated every time a key expires)
#  e     Evicted events (events generated when a key is evicted for maxmemory)
#  A     Alias for g$lshzxe, so that the "AKE" string means all the events.
#
#  The "notify-keyspace-events" takes as argument a string that is composed
#  of zero or multiple characters. The empty string means that notifications
#  are disabled.
#
#  Example: to enable list and generic events, from the point of view of the
#           event name, use:
#
#  notify-keyspace-events Elg
#
#  Example 2: to get the stream of the expired keys subscribing to channel
#             name __keyevent@0__:expired use:
#
#  notify-keyspace-events Ex
#
#  By default all notifications are disabled because most users don't need
#  this feature and the feature has some overhead. Note that if you don't
#  specify at least one of K or E, no events will be delivered.
notify-keyspace-events ""

二、整合方案

1、自定义监听事件

该方案是自定义监听器messageListener,监听指定的频道"__keyevent@*",表示监听所有事件,这种方案比较灵活,可以自定义监听的事件频道。但是,这种需要redis服务配置开启通知,例如配置notify-keyspace-events为AKE,表示开启全部事件通知。如果redis配置不正确,是不会通知指定事件的。另外,如果修改了该配置还需要重启Redis服务,所以慎重选择该方式。

redis配置如下:

# redis配置开启全部事件通知
notify-keyspace-events AKE

 代码部分如下:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.listener.PatternTopic;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.listener.adapter.MessageListenerAdapter;

@Configuration
public class RedisListenerConfig {

    @Bean
    public RedisMessageListenerContainer container(RedisConnectionFactory connectionFactory, MessageListenerAdapter listenerAdapter) {

        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(connectionFactory);
        // 订阅一个全部变化事件频道 __keyevent@*
        container.addMessageListener(listenerAdapter, new PatternTopic("__keyevent@*"));

        return container;
    }

    @Bean
    MessageListenerAdapter listenerAdapter() {
        // 如果使用自定义方法myHandleMessage,就把方法名作为第二个参数添入
        // return new MessageListenerAdapter(new RedisKeyChangeSubscriber(), "myHandleMessage");
        // 如果不传入第二个参数,则会使用默认方法handleMessage
        return new MessageListenerAdapter(new RedisKeyChangeSubscriber());
    }

    public static class RedisKeyChangeSubscriber {
        // 自定义处理方法
        public void myHandleMessage(String message) {
            System.out.println("RedisKeyChangeSubscriber Received message: " + message);
            // 在这里处理收到的消息
        }

        // message对应redis数据的key
        public void handleMessage(String message) {
            System.out.println("RedisKeyChangeSubscriber Received message: " + message);
            // 在这里处理收到的消息
        }
    }
}

测试效果:

①创建键值对{"key1": "val1"}

2、继承spring boot集成的监听器KeyspaceEventMessageListener

spring官方提供的redis starter依赖包含了事件变化监听器KeyspaceEventMessageListener,是个抽象类,可以通过继承这个抽象类重写doHandleMessage方法来自定义数据变化的处理逻辑。这种方式不需要关注Redis配置,简化了监听事件变化的处理,容易上手。没有特别要求的话,也推荐使用这种方式。同样的,该依赖也提供了redis数据过期事件的监听器KeyExpirationEventMessageListener,用于监听redis数据过期的事件,使用方法和KeyspaceEventMessageListener大体一致,但是KeyExpirationEventMessageListener不是抽象类。

import org.jetbrains.annotations.NotNull;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.Message;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.listener.KeyspaceEventMessageListener;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.listener.adapter.MessageListenerAdapter;

@Configuration
public class RedisListenerConfig {

    @Bean
    public RedisMessageListenerContainer container(RedisConnectionFactory connectionFactory) {

        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(connectionFactory);

        return container;
    }

    @Bean
    RedisKeyChangerHandler redisKeyChangerHandler(RedisMessageListenerContainer container) {
        return new RedisKeyChangerHandler(container);
    }

    public static class RedisKeyChangerHandler extends KeyspaceEventMessageListener {
        /**
         * Creates new {@link KeyspaceEventMessageListener}.
         *
         * @param listenerContainer must not be {@literal null}.
         */
        public RedisKeyChangerHandler(RedisMessageListenerContainer listenerContainer) {
            super(listenerContainer);
        }

        @Override
        // message对应redis数据的key
        protected void doHandleMessage(@NotNull Message message) {
            System.out.println("KeyspaceEventMessageListener Received message: " + message);
        }
    }
}

测试效果同方案一。 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/539077.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Spring Boot | SpringBoot 对 SpringMVC的 “整合支持“

目录: SpringMVC 的 “整合支持” ( 引入"Web依赖启动器"&#xff0c;几乎可以在无任何额外的配置的情况下进行"Web开发")1.SpringMVC "自动配置" 介绍 ( 引入Web依赖启动器"后&#xff0c;SpringBoot会自动进行一些“自动配置”&#xff0…

【Hadoop】下载安装及伪分布式集群搭建教程

目录 1.概述 2.环境准备 3.hadoop安装 3.1.下载安装配置 3.2.伪分布式集群 3.3.注意事项 4.Hadoop集群的组成 1.概述 hadoop有三种安装模式 单机模式&#xff0c;只在一台机器上运行&#xff0c;存储用的本地文件系统而不是HDFS。 伪分布式模式&#xff0c;存储采用HD…

221 基于matlab编制的直齿圆柱齿轮应力计算程序

基于matlab编制的直齿圆柱齿轮应力计算程序&#xff0c;输入设计参数&#xff1a;模数、齿顶高、齿宽、啮合齿数、转速、扭矩、安全系数、压力角、齿轮类型&#xff08;开式、闭式&#xff09;等&#xff0c;输出弯曲应力和许用应力&#xff0c;并对比是否满足要求。并把程序成…

【算法刷题 | 回溯思想 02】4.12(电话号码的字母组合)

文章目录 4.电话号码的字母组合4.1问题4.2解法&#xff1a;回溯4.2.1回溯思路&#xff08;1&#xff09;函数返回值以及参数&#xff08;2&#xff09;终止条件&#xff08;3&#xff09;遍历过程 4.2.2代码实现 4.电话号码的字母组合 4.1问题 给定一个仅包含数字 2-9 的字符…

B站基于Apache Ranger的大数据权限服务的技术演进

01 背景 随着云计算、大数据技术的日趋成熟&#xff0c;复杂多元、规模庞大的数据所蕴含的经济价值和社会价值逐步凸显&#xff0c;数据安全也是企业面临的巨大挑战&#xff0c;B站一直致力于对用户隐私数据的保护。 02 Ranger概述 2.1 用户认证 提到安全&#xff0c;就不得不…

【数学建模】2024认证杯C题完整思路和代码论文解析

经过不懈的努力&#xff0c;2024认证杯数学建模C题的完整论文和代码已完成&#xff0c;代码为A题全部4问的代码&#xff0c;论文包括摘要、问题重述、问题分析、模型假设、符号说明、模型的建立和求解&#xff08;问题1模型的建立与求解、问题2模型的建立与求解、问题3模型的建…

贪心算法:柠檬水找零

题目链接&#xff1a;860. 柠檬水找零 - 力扣&#xff08;LeetCode&#xff09; 收的钱只能是5、10、20美元&#xff0c;分类讨论&#xff1a;收5美元无需找零&#xff1b;收10美元找零5元&#xff1b;收20美元找零15美元。其中对于找零15美元的方案有两种&#xff0c;此处涉及…

论文阅读:Polyp-PVT: Polyp Segmentation with PyramidVision Transformers

这篇论文提出了一种名为Polyp-PVT的新型息肉分割框架&#xff0c;该框架采用金字塔视觉变换器&#xff08;Pyramid Vision Transformer, PVT&#xff09;作为编码器&#xff0c;以显式提取更强大的特征。本模型中使用到的关键技术有三个&#xff1a;渐进式特征融合、通道和空间…

QLoRa 低秩分解+权重量化的微调

QLoRa的核心思想是首先使用低秩分解技术降低参数的数量&#xff0c;然后对这些低秩表示的参数应用量化技术&#xff0c;进一步减少所需的存储空间和计算量。 https://arxiv.org/abs/2305.14314 低秩分解 低秩分解&#xff08;Low-Rank Factorization&#xff09;&#xff1a;…

什么是RMVB视频?如何把视频转成RMVB格式?视频格式转换的方法

一&#xff0c;什么是RMVB视频格式 RMVB是一种视频文件格式&#xff0c;它基于RealNetworks公司开发的RealMedia编解码器&#xff0c;被广泛应用于互联网上的视频流媒体传输和下载。RMVB文件通常具有较小的文件大小&#xff0c;同时保持较高的视频质量&#xff0c;因此在网络传…

python爬虫 - 下载图片

文章目录 1、下载图片示例1&#xff1a;使用 .urlretrieve() 函数2、下载图片示例2 - 使用 open/write 函数3、下载图片示例33.1 使用 open/write 下载3.2 使用 urlretrieve下载 爬虫的本质&#xff1a;模拟对应的App&#xff0c;浏览器访问对应的地址获取到数据 1、下载图片示…

ElasticView一款ElasticSearch的web可视化工具

ElasticView 是一款用来监控ElasticSearch状态和操作ElasticSearch索引的web可视化工具。它由golang开发而成&#xff0c;具有部署方便&#xff0c;占用内存小等优点 ElasticSearch连接树管理&#xff08;更方便的切换测试/生产环境&#xff09;支持权限管理支持sql转换成dsl语…

问题汇总

一、TCP的粘包和拆包问题&#xff1f; TCP在发送和接受数据的时候&#xff0c;有一个滑动窗口来控制接受数据的大小&#xff0c;这个滑动窗口你就可以理解为一个缓冲区的大小。缓冲区满了就会把数据发送&#xff0c;数据包的大小是不固定的&#xff0c;有时候比缓冲区大有时候…

[论文笔记] Pai-megatron Qwen1.5-14B-CT 后预训练 踩坑记录

1. 模型权重转换报错 hf2mcore_1.5_v2.py 报错为: /mnt/cpfs/kexin/dlc_code/qwen1.5/PAI-Megatron-Patch/toolkits/model_checkpoints_convertor/qwen/hf2mcore_1.5_v2.py 正确文件替换如下,更改了477行,删除了 args.hidden_size 这个维度,在tp>1时也支持转换: eli…

网盘——搜索用户

目录 1、搜索用户 1.1、在friend.h里面定义槽函数 1.2、关联槽函数 1.3、搜索用户的时候&#xff0c;会弹出一个对话框来,在friend.cpp里面引入下面的头文件&#xff0c;专门用来输入数据的 1.4、获取输入信息&#xff0c;并使用Qstring来接收它 1.5、将上述代码打包&…

嵌入式:第二天(C语言入门)

目录 一、基础语法 位运算符&#xff1a; & -&#xff08;与运算&#xff09; | -&#xff08;或运算&#xff09; ^ -&#xff08;异或运算&#xff09; ~ -&#xff08;取反运算&#xff09; << -&#xff08;左移运算符&#xff09; >> -&#xff0…

稀碎从零算法笔记Day47-LeetCode:找到冠军 I

或许是昨天的每日一题太难了&#xff0c;今天的简单 题型&#xff1a;数组、矩阵 链接&#xff1a;2923. 找到冠军 I - 力扣&#xff08;LeetCode&#xff09; 来源&#xff1a;LeetCode 题目描述 一场比赛中共有 n 支队伍&#xff0c;按从 0 到 n - 1 编号。 给你一个下…

深入理解Apache ZooKeeper与Kafka的协同工作原理

目录 引言 一、ZooKeeper基础概念 &#xff08;一&#xff09;ZooKeeper简介 &#xff08;二&#xff09;ZooKeeper数据结构 &#xff08;三&#xff09;ZooKeeper特点 &#xff08;四&#xff09;应用场景 二、ZooKeeper工作模式 &#xff08;一&#xff09;工作机制 …

未来汽车硬件安全的需求(2)

目录 4.汽车安全控制器 4.1 TPM2.0 4.2 安全控制器的硬件保护措施 5. EVITA HSM和安全控制器结合 6.小结 4.汽车安全控制器 汽车安全控制器是用于汽车工业安全关键应用的微控制器。 他们的保护水平远远高于EVITA HSM。今天的典型应用是移动通信&#xff0c;V2X、SOTA、…

享元模式:优化资源利用的高效策略

在面向对象的软件开发中&#xff0c;享元模式是一种结构型设计模式&#xff0c;旨在减少内存使用&#xff0c;通过共享尽可能多的相似对象来提高应用程序的效率。本文将详细介绍享元模式的定义、实现、应用场景以及优缺点。 1. 享元模式的定义 享元模式&#xff08;Flyweigh…