spring-boot-starter-data-redis 配置自定义缓存到期时间

简述: springboot + spring-boot-starter-data-redis 配置redis(单机) , 主要记录配置不同缓存块到期时间

1.导入依赖 | spring-boot-starter-data-redis 和commons-pool2 这两个依赖, 在spring-boot-starter-parent [spring-boot-dependencies] 里面, 这里只需要在自己的项目pom中声明使用它即可

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
	<groupId>org.apache.commons</groupId>
	<artifactId>commons-pool2</artifactId>
</dependency>

2. 配置文件 | 使用位置位于:  org.springframework.boot.autoconfigure.data.redis

spring:
  redis:
    host: 152.148.489.949(安装redis的ip,本机则用127.0.0.1)
    port: 6379
    password: 你的redis登录密码(没有设置则不填)
    database: 0
    lettuce:
      pool:
        max-idle: 8 # 连接池中的最大空闲连接 默认8
        min-idle: 0  # 连接池中的最小空闲连接 默认0
        max-active: 8  # 连接池最大连接数 默认8 ,负数表示没有限制
        max-wait: -1 # 连接池最大阻塞等待时间(使用负值表示没有限制) 默认-1
    timeout: 20000

3.自定义缓存块接口 | 集中管理缓存块名称和对应到期时间

import java.lang.reflect.Field;
import java.time.Duration;
import java.util.*;

/**
 *  缓存块名称/生存时间, 集合
 *  命名规则: 缓存块名称任意,缓存快数据到期时间不指定,则默认永久.
 *           指定则为: 缓存块名_DURATION
 * */
public interface CacheNameBlock {

    String USER_INFO = "userInfo:list"; // 缓存块名称
    Duration USER_INFO_DURATION = Duration.ofSeconds(180); // 对应缓存块到期时间

    String USER_INFO_2 = "userInfo:list2"; // 缓存块名称2 - 不配置到期时间则默认存活永久

    // 用于Redis缓存管理器,自定义缓存块到期时间管理
    static List<Map<String,Object>> toList(){
        List<Map<String, Object>> result = new ArrayList<>();
        try {
            // 所有字段
            Class<CacheNameBlock> cacheNameBlockClass = CacheNameBlock.class;
            Field[] declaredFields = cacheNameBlockClass.getDeclaredFields();
            for (Field declaredField : declaredFields) {
                String name = declaredField.getName();
                if (!name.contains("DURATION")) {
                    Map<String, Object> addMap = new HashMap<>();
                    addMap.put("cacheBlockName",declaredField.get(String.class));
                    // 找到对应时间
                    name = name+"_DURATION";
                    try{
                        Field field = cacheNameBlockClass.getField(name);
                        addMap.put("expirationTime",field.get(Duration.class));
                    } catch (Exception e) {
                        addMap.put("expirationTime",Duration.ofSeconds(-1));
                    }
                    result.add(addMap);
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return result;
    }

}

4.创建RedisConfiguration配置类 | 实现修改缓存数据格式, 管理自定义缓存块

import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.cache.RedisCacheConfiguration;
import org.springframework.data.redis.cache.RedisCacheManager;
import org.springframework.data.redis.cache.RedisCacheWriter;
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.*;
import java.time.Duration;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

/**
 * redis配置类
 * @Configuration - 将该类置为配置类
 * @EnableCaching - 开启缓存注解的使用
 *
 */
@Configuration // 将该类置为配置类
@EnableCaching // 开启缓存注解的使用
public class RedisConfiguration {

    /**
     * Redis缓存管理器 (针对使用@Cacheable 缓存注解存储时的配置)
     * */
    @Bean
    public CacheManager redisCacheManager(LettuceConnectionFactory connectionFactory) {

        // Redis序列化上下文。序列化键值对
        RedisSerializationContext.SerializationPair<String> key = RedisSerializationContext.SerializationPair.fromSerializer(keySerializer());
        RedisSerializationContext.SerializationPair<Object> value = RedisSerializationContext.SerializationPair.fromSerializer(valueSerializer());

        // 生成默认Redis配置: 未指定自定义缓存块时, 其他所有缓存数据都以该配置为生成依据
        RedisCacheConfiguration defaultRedisCacheConfiguration = getRedisCacheConfiguration(Duration.ofSeconds(-1), key, value);// 默认缓存时间永久,禁用缓存空值

        // 生成自定义缓存块,redis配置(这个取决于项目中是否有需要在使用@Cacheable缓存数据时,希望有不同的过期时间再决定是否使用)
        Map<String, RedisCacheConfiguration> customCacheBlockConfig = new LinkedHashMap<>();
        List<Map<String, Object>> list = CacheNameBlock.toList(); // 从自定义的enum(枚举类)拿到设置缓存块名称及对应的生存时间值
        list.stream().forEach(item-> {
            customCacheBlockConfig.put((String)item.get("cacheBlockName"),getRedisCacheConfiguration((Duration)item.get("expirationTime"),key,value)); // 缓存时间
        });

        // 生成 CacheManager
        return RedisCacheManager
                .builder(RedisCacheWriter.nonLockingRedisCacheWriter(connectionFactory)) // 非锁定Redis缓存编写器
                .cacheDefaults(defaultRedisCacheConfiguration) // 缓存默认值配置
                .withInitialCacheConfigurations(customCacheBlockConfig) // 自定义缓存默认值配置
                .build(); // 建立
    }

    /**
     * Redis模板 (针对使用底层提供的 RedisTemplate 对数据操作进行的配置修改)
     * */
    @Bean
    public RedisTemplate<String, Integer> redisTemplate(LettuceConnectionFactory factory) {
        RedisTemplate<String, Integer> redisTemplate = new RedisTemplate<>();
        redisTemplate.setKeySerializer(keySerializer());
        redisTemplate.setValueSerializer(valueSerializer());
        redisTemplate.setHashKeySerializer(keySerializer());
        redisTemplate.setHashValueSerializer(valueSerializer());
        redisTemplate.setExposeConnection(true);
        redisTemplate.setConnectionFactory(factory);
        redisTemplate.afterPropertiesSet();
        return redisTemplate;
    }

    /**
     * 生成Redis缓存配置
     * */
    private RedisCacheConfiguration getRedisCacheConfiguration(
            Duration expirationTime,
            RedisSerializationContext.SerializationPair<String> key,
            RedisSerializationContext.SerializationPair<?> value
    ) {
        RedisCacheConfiguration redisCacheConfiguration = RedisCacheConfiguration.defaultCacheConfig()
                .entryTtl(expirationTime) // 默认缓存时间永久
                .serializeKeysWith(key) // 默认序列化键方式
                .serializeValuesWith(value) // 默认序列化值方式
                .computePrefixWith(name -> name + ":") //变双冒号为单冒号
                .disableCachingNullValues(); // 禁用缓存空值
        return redisCacheConfiguration;
    }

    /**
     * 序列化键
     * */
    private RedisSerializer<String> keySerializer() {
        return new StringRedisSerializer();
    }

    /**
     * 序列化值
     * */
    private RedisSerializer<Object> valueSerializer(){
        return new Jackson2JsonRedisSerializer(Object.class);
    }

}

5.示例 | 使用缓存注解@Cacheable - 上面自定义的接口到期时间, 主要用于使用缓存注解时候, 方便控制注解缓存到期时间

@GetMapping("selectOne")
@ApiOperation(value = "测试")
@Cacheable(value = CacheNameBlock.USER_INFO_2, key = "methodName")
public String selectOne() {
	return "test";
}

 

说明:

(1) 主要是把缓存块放到一个接口里面进行管理, 在配置类里拿到该接口定义的所有缓存块名称和到期时间, 这样以后项目想新增不同到期时间的缓存块名称时, 不需要更改配置类.

(2) 记得检查上面两个jar包是否下载到你本地了, 之前配置时候, 出现未下载成功,然后启动报错的情况

(3) 工具类在这里不写了, 使用工具类有局限性, 个人不喜欢用

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值