Spring boot实现监听Redis key失效事件

Spring boot实现监听Redis key失效事件

1、添加相关依赖

 <!-- redis -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-redis</artifactId>
        </dependency>

2、配置监听(可全部库监听和选一个库监听)

@Configuration
public class RedisListenerConfig {
    @Bean
    RedisMessageListenerContainer container(RedisConnectionFactory connectionFactory) {
 
        RedisMessageListenerContainer container = new RedisMessageListenerContainer();
        container.setConnectionFactory(connectionFactory);
        // 选一个库监听则打开下一行的注释
        //container.addMessageListener(new RedisExpiredListener(), new PatternTopic("__keyevent@0__:expired"));
        return container;
    }
}

3.a选一个库监听

/**
 * @author mazhq
 * @Title: RedisKeyExpirationListener
 * @ProjectName: zeus
 * @date 2019/2/20 11:26
 */
@Component
public class RedisKeyExpirationListener extends KeyExpirationEventMessageListener {
    private final static Logger logger = LoggerFactory.getLogger(RedisKeyExpirationListener.class);
    @Autowired
    private RedisClient redisClient;
    /**
     * Creates new {@link MessageListener} for {@code __keyevent@*__:expired} messages.
     *
     * @param listenerContainer must not be {@literal null}.
     */
    public RedisKeyExpirationListener(RedisMessageListenerContainer listenerContainer) {
        super(listenerContainer);
    }
 
    @Override
    public void onMessage(Message message, byte[] pattern) {
        // 用户做自己的业务处理即可,注意message.t`在这里插入代码片`oString()可以获取失效的key
        String expiredKey = message.toString();
        if(expiredKey.startsWith("zeus:order")){
            //TODO
        }
    }
}

3.b指定某库监听

public class RedisExpiredListener implements MessageListener {
 
    /**
     * 客户端监听订阅的topic,当有消息的时候,会触发该方法;
     * 并不能得到value, 只能得到key。
     * 姑且理解为: redis服务在key失效时(或失效后)通知到java服务某个key失效了, 那么在java中不可能得到这个redis-key对应的redis-value。
     *      * 解决方案:
     *  创建copy/shadow key, 例如 set vkey "vergilyn"; 对应copykey: set copykey:vkey "" ex 10;
     *  真正的key是"vkey"(业务中使用), 失效触发key是"copykey:vkey"(其value为空字符为了减少内存空间消耗)。
     *  当"copykey:vkey"触发失效时, 从"vkey"得到失效时的值, 并在逻辑处理完后"del vkey"
     *
     * 缺陷:
     *  1: 存在多余的key; (copykey/shadowkey)
     *  2: 不严谨, 假设copykey在 12:00:00失效, 通知在12:10:00收到, 这间隔的10min内程序修改了key, 得到的并不是 失效时的value.
     *  (第1点影响不大; 第2点貌似redis本身的Pub/Sub就不是严谨的, 失效后还存在value的修改, 应该在设计/逻辑上杜绝)
     *  当"copykey:vkey"触发失效时, 从"vkey"得到失效时的值, 并在逻辑处理完后"del vkey"
     *
     */
    @Override
    public void onMessage(Message message, byte[] bytes) {
        byte[] body = message.getBody();// 建议使用: valueSerializer
        byte[] channel = message.getChannel();
        System.out.print("onMessage >> " );
        System.out.println(String.format("channel: %s, body: %s, bytes: %s"
                ,new String(channel), new String(body), new String(bytes)));
    }
 
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Spring Boot 中使用 Redis 监听删除事件,可以结合使用 RedisTemplate 和 Spring Data Redis 提供的监听器(EventListener),具体实现步骤如下: 1. 创建一个 RedisTemplate 对象,用于操作 Redis 数据库: ```java @Configuration public class RedisConfig { @Bean public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) { RedisTemplate<String, Object> template = new RedisTemplate<>(); template.setConnectionFactory(factory); template.setKeySerializer(new StringRedisSerializer()); template.setValueSerializer(new GenericJackson2JsonRedisSerializer()); template.afterPropertiesSet(); return template; } } ``` 2. 创建一个 RedisKeyExpirationListener 类,实现 RedisKeyExpiredEvent 事件的处理方法: ```java @Component public class RedisKeyExpirationListener implements ApplicationListener<RedisKeyExpiredEvent> { @Override public void onApplicationEvent(RedisKeyExpiredEvent event) { String key = event.getSource().toString(); System.out.println("Key expired: " + key); } } ``` 3. 在 RedisTemplate 对象上注册监听器: ```java @Configuration public class RedisConfig { @Autowired private RedisKeyExpirationListener redisKeyExpirationListener; @Bean public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) { RedisTemplate<String, Object> template = new RedisTemplate<>(); template.setConnectionFactory(factory); template.setKeySerializer(new StringRedisSerializer()); template.setValueSerializer(new GenericJackson2JsonRedisSerializer()); template.afterPropertiesSet(); // 注册监听器 template.setEnableTransactionSupport(true); template.getConnectionFactory().getConnection().subscribe(new MessageListenerAdapter(redisKeyExpirationListener)); return template; } } ``` 在这个例子中,我们使用 RedisKeyExpiredEvent 事件监听 Redis 中的键过期事件。当 Redis 中的键过期时,会触发 RedisKeyExpiredEvent 事件事件源是被删除的键名。在 RedisKeyExpirationListener 中,我们实现 onApplicationEvent 方法,打印出被删除的键名。 在 RedisTemplate 注册监听器的过程中,我们使用了 MessageListenerAdapter 类将 RedisKeyExpirationListener 转化为 MessageListener 对象,然后订阅 Redis 的键事件频道。当 Redis 中有键事件发生时,MessageListenerAdapter 会将事件转发给 RedisKeyExpirationListener 处理。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值