本文轉載自:https://www.cnblogs.com/a565810497/p/10937477.html
之前嘗試了一下springboot集成springcahce:https://www.cnblogs.com/a565810497/p/10931426.html
又嘗試了用guava設置springcahce的有效時長:https://www.cnblogs.com/a565810497/p/10932149.html
但是終究覺得不太靈活,因為guava設置有效時長只是設置默認的,不能設置多個,而且springcahce不是緩存在數據庫上的,那么redis就很適合和springcahce集合起來
首先我們要使用springcahce集成redis先,參考文章:https://blog.battcn.com/2018/05/13/springboot/v2-cache-redis/
添加依賴
在porm.xml添加redis的依賴
<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> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency>
屬性配置
## Redis服務器地址 spring.redis.host=127.0.0.1 ## Redis服務器連接端口 spring.redis.port=6379 ## Redis服務器連接密碼(默認為空) spring.redis.password= # 一般來說是不用配置的,Spring Cache 會根據依賴的包自行裝配 spring.cache.type=redis # 連接超時時間(毫秒) spring.redis.timeout=10000 # Redis默認情況下有16個分片,這里配置具體使用的分片 spring.redis.database=0 # 連接池最大連接數(使用負值表示沒有限制) 默認 8 spring.redis.lettuce.pool.max-active=8 # 連接池最大阻塞等待時間(使用負值表示沒有限制) 默認 -1 spring.redis.lettuce.pool.max-wait=-1 # 連接池中的最大空閑連接 默認 8 spring.redis.lettuce.pool.max-idle=8 # 連接池中的最小空閑連接 默認 0 spring.redis.lettuce.pool.min-idle=0
然后我們就可以基於redis設置springcache的有效時間了,參考文章:https://blog.csdn.net/weixin_42047790/article/details/84189275
在啟動類配置有效時長:
@Bean public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) { return new RedisCacheManager( RedisCacheWriter.nonLockingRedisCacheWriter(redisConnectionFactory), this.getRedisCacheConfigurationWithTtl(30*60), // 默認策略,未配置的 key 會使用這個 this.getRedisCacheConfigurationMap() // 指定 key 策略 ); } private Map<String, RedisCacheConfiguration> getRedisCacheConfigurationMap() { Map<String, RedisCacheConfiguration> redisCacheConfigurationMap = new HashMap<>(); //DayCache和SecondsCache進行過期時間配置 redisCacheConfigurationMap.put("DayCache", this.getRedisCacheConfigurationWithTtl(24*60*60)); redisCacheConfigurationMap.put("SecondsCache", this.getRedisCacheConfigurationWithTtl(2)); return redisCacheConfigurationMap; } private RedisCacheConfiguration getRedisCacheConfigurationWithTtl(Integer seconds) { Jackson2JsonRedisSerializer<Object> jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer<>(Object.class); ObjectMapper om = new ObjectMapper(); om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY); om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL); jackson2JsonRedisSerializer.setObjectMapper(om); RedisCacheConfiguration redisCacheConfiguration = RedisCacheConfiguration.defaultCacheConfig(); redisCacheConfiguration = redisCacheConfiguration.serializeValuesWith( RedisSerializationContext .SerializationPair .fromSerializer(jackson2JsonRedisSerializer) ).entryTtl(Duration.ofSeconds(seconds)); return redisCacheConfiguration; } @Bean public KeyGenerator wiselyKeyGenerator() { return new KeyGenerator() { @Override public Object generate(Object target, Method method, Object... params) { StringBuilder sb = new StringBuilder(); sb.append(target.getClass().getName()); sb.append("." + method.getName()); if(params==null||params.length==0||params[0]==null){ return null; } String join = String.join("&", Arrays.stream(params).map(Object::toString).collect(Collectors.toList())); String format = String.format("%s{%s}", sb.toString(), join); //log.info("緩存key:" + format); return format; } }; }
分別使用不同時長的cache:
@Override @Cacheable(value = "SecondsCache") public TestTime getTestTime(){ return new TestTime(new Date()); } @Override @Cacheable(value = "DayCache") public TestTime getTestTime1(){ return new TestTime(new Date()); }
Secondscache是設置了2秒的生命周期。
DayCache是設置了一天的生命周期。
為什么要那么繁瑣的設置呢,其實redis已經可以在添加緩存的時候設置有效時間,但是我們是想用注解的方式 @cacheable 做到不需要代碼侵入來實現注解,於是就結合redis和springcahce。