<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-data-redisartifactId>
dependency>
redis:
host: 127.0.0.1
port: 6379
timeout: 3000
package com.strap.mydemo.config;
import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.jsontype.impl.LaissezFaireSubTypeValidator;
import lombok.extern.log4j.Log4j;
import org.springframework.cache.Cache;
import org.springframework.cache.interceptor.CacheErrorHandler;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
/**
* 消息监听配置
*
* @author strap
*/
@Configuration
@Log4j
public class RedisConfig {
public RedisConfig() {
}
@Bean
public RedisTemplate<String, Object> initTemplate(RedisConnectionFactory factory) {
RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
redisTemplate.setConnectionFactory(factory);
Jackson2JsonRedisSerializer<Object> valueSerializer = new Jackson2JsonRedisSerializer<>(Object.class);
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
objectMapper.activateDefaultTyping(LaissezFaireSubTypeValidator.instance, ObjectMapper.DefaultTyping.NON_FINAL);
valueSerializer.setObjectMapper(objectMapper);
StringRedisSerializer keySerializer = new StringRedisSerializer();
// key均采用string的序列化方式
redisTemplate.setKeySerializer(keySerializer);
redisTemplate.setHashKeySerializer(keySerializer);
// value均采用jackson序列化
redisTemplate.setValueSerializer(valueSerializer);
redisTemplate.setHashValueSerializer(valueSerializer);
redisTemplate.setEnableTransactionSupport(true);
redisTemplate.afterPropertiesSet();
return redisTemplate;
}
/**
* redis数据操作异常处理
* 这里的处理:在日志中打印出错误信息,但是放行
* 保证redis服务器出现连接等问题的时候不影响程序的正常运行,使得能够出问题时不用缓存
*/
@Bean
public CacheErrorHandler errorHandler() {
return new CacheErrorHandler() {
@Override
public void handleCacheGetError(RuntimeException e, Cache cache, Object key) {
log.error("redis异常:key=[{" + key + "}]", e);
}
@Override
public void handleCachePutError(RuntimeException e, Cache cache, Object key, Object value) {
log.error("redis异常:key=[{" + key + "}]", e);
}
@Override
public void handleCacheEvictError(RuntimeException e, Cache cache, Object key) {
log.error("redis异常:key=[{" + key + "}]", e);
}
@Override
public void handleCacheClearError(RuntimeException e, Cache cache) {
log.error("redis异常:", e);
}
};
}
}
修改其中的配置,打开监听
将 notify-keyspace-events ""
修改为 notify-keyspace-events "Ex"
重启redis服务
命令详解
开启键空间通知功能需要消耗一些CPU,所以在默认配置下,该功能处于关闭状态。
notify-keyspace-events 的参数可以是以下字符的任意组合,它指定了服务器该发送哪些类型的通知
- K :键空间通知,所有通知以_keyspace@为前缀
- E: 键事件通知,所有通知以_keyevent@为前缀
- g: DEL 、 EXPIRE 、RENAME 等类型无关的通用命令的通知
- $:字符串命令的通知
- l:列表命令的通知
- s:集合命令的通知
- h:哈希命令的通知
- z:有序集合命令的通知
- x:过期事件,每当有过期键被删除时发送
- d:驱逐(evict)事件:每当有键因为maxmemory政策而被删除时发送
- A:参数g$lshzxe的别名
输入的参数中至少要有一个K或者E,否则的话,不管其余的参数是什么,都不会有任何通知被分发
redis-start.bat
redis-start.bat
,选择你需要监听的库,即@后面的值,redis默认配置连接的是0号库,运行命令psubscribe __keyevent@0__:expired
SETEX mykey 3 redis
/**
* 配置监听
*/
@Bean
public RedisMessageListenerContainer messageListenerContainer(RedisConnectionFactory redisConnectionFactory) throws Exception {
RedisMessageListenerContainer container = new RedisMessageListenerContainer();
container.setConnectionFactory(redisConnectionFactory);
return container;
}
package com.strap.mydemo.components;
import lombok.extern.log4j.Log4j;
import org.springframework.data.redis.connection.Message;
import org.springframework.data.redis.listener.KeyExpirationEventMessageListener;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.stereotype.Component;
/**
*
*
* @author strap
*/
@Log4j
@Component
public class KeyExpiredListener extends KeyExpirationEventMessageListener {
public KeyExpiredListener(RedisMessageListenerContainer container) {
super(container);
}
@Override
public void onMessage(Message message, byte[] pattern) {
log.info("这是被销毁的Key:" + message.toString());
}
}