Skip to content

Commit 4a9123d

Browse files
committed
Detect user-defined RedisCacheConfiguration
This commits improves the cache auto-configuration for Redis by looking up a custom "RedisCacheConfiguration" bean that allows to take full control over the `RedisCacheManager`. Closes gh-11599
1 parent 7d12dc2 commit 4a9123d

File tree

3 files changed

+56
-11
lines changed

3 files changed

+56
-11
lines changed

spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/cache/RedisCacheConfiguration.java

+12-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2017 the original author or authors.
2+
* Copyright 2012-2018 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -19,6 +19,7 @@
1919
import java.util.LinkedHashSet;
2020
import java.util.List;
2121

22+
import org.springframework.beans.factory.ObjectProvider;
2223
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
2324
import org.springframework.boot.autoconfigure.cache.CacheProperties.Redis;
2425
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
@@ -51,24 +52,31 @@ class RedisCacheConfiguration {
5152

5253
private final CacheManagerCustomizers customizerInvoker;
5354

55+
private final org.springframework.data.redis.cache.RedisCacheConfiguration redisCacheConfiguration;
56+
5457
RedisCacheConfiguration(CacheProperties cacheProperties,
55-
CacheManagerCustomizers customizerInvoker) {
58+
CacheManagerCustomizers customizerInvoker,
59+
ObjectProvider<org.springframework.data.redis.cache.RedisCacheConfiguration> redisCacheConfiguration) {
5660
this.cacheProperties = cacheProperties;
5761
this.customizerInvoker = customizerInvoker;
62+
this.redisCacheConfiguration = redisCacheConfiguration.getIfAvailable();
5863
}
5964

6065
@Bean
6166
public RedisCacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) {
6267
RedisCacheManagerBuilder builder = RedisCacheManager
63-
.builder(redisConnectionFactory).cacheDefaults(getConfiguration());
68+
.builder(redisConnectionFactory).cacheDefaults(determineConfiguration());
6469
List<String> cacheNames = this.cacheProperties.getCacheNames();
6570
if (!cacheNames.isEmpty()) {
6671
builder.initialCacheNames(new LinkedHashSet<>(cacheNames));
6772
}
6873
return this.customizerInvoker.customize(builder.build());
6974
}
7075

71-
private org.springframework.data.redis.cache.RedisCacheConfiguration getConfiguration() {
76+
private org.springframework.data.redis.cache.RedisCacheConfiguration determineConfiguration() {
77+
if (this.redisCacheConfiguration != null) {
78+
return this.redisCacheConfiguration;
79+
}
7280
Redis redisProperties = this.cacheProperties.getRedis();
7381
org.springframework.data.redis.cache.RedisCacheConfiguration config = org.springframework.data.redis.cache.RedisCacheConfiguration
7482
.defaultCacheConfig();

spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/cache/CacheAutoConfigurationTests.java

+40-7
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2012-2017 the original author or authors.
2+
* Copyright 2012-2018 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -279,7 +279,7 @@ public void couchbaseCacheExplicitWithTtl() {
279279

280280
@Test
281281
public void redisCacheExplicit() {
282-
this.contextRunner.withUserConfiguration(RedisCacheConfiguration.class)
282+
this.contextRunner.withUserConfiguration(RedisConfiguration.class)
283283
.withPropertyValues("spring.cache.type=redis",
284284
"spring.cache.redis.time-to-live=15000",
285285
"spring.cache.redis.cacheNullValues=false",
@@ -300,17 +300,36 @@ public void redisCacheExplicit() {
300300
});
301301
}
302302

303+
@Test
304+
public void redisCacheWithRedisCacheConfiguration() {
305+
this.contextRunner
306+
.withUserConfiguration(RedisWithCacheConfigurationConfiguration.class)
307+
.withPropertyValues("spring.cache.type=redis",
308+
"spring.cache.redis.time-to-live=15000",
309+
"spring.cache.redis.keyPrefix=foo")
310+
.run((context) -> {
311+
RedisCacheManager cacheManager = getCacheManager(context,
312+
RedisCacheManager.class);
313+
assertThat(cacheManager.getCacheNames()).isEmpty();
314+
org.springframework.data.redis.cache.RedisCacheConfiguration redisCacheConfiguration = (org.springframework.data.redis.cache.RedisCacheConfiguration) new DirectFieldAccessor(
315+
cacheManager).getPropertyValue("defaultCacheConfig");
316+
assertThat(redisCacheConfiguration.getTtl())
317+
.isEqualTo(java.time.Duration.ofSeconds(30));
318+
assertThat(redisCacheConfiguration.getKeyPrefix()).contains("bar");
319+
});
320+
}
321+
303322
@Test
304323
public void redisCacheWithCustomizers() {
305324
this.contextRunner
306-
.withUserConfiguration(RedisCacheAndCustomizersConfiguration.class)
325+
.withUserConfiguration(RedisWithCustomizersConfiguration.class)
307326
.withPropertyValues("spring.cache.type=" + "redis")
308327
.run(dunno("allCacheManagerCustomizer", "redisCacheManagerCustomizer"));
309328
}
310329

311330
@Test
312331
public void redisCacheExplicitWithCaches() {
313-
this.contextRunner.withUserConfiguration(RedisCacheConfiguration.class)
332+
this.contextRunner.withUserConfiguration(RedisConfiguration.class)
314333
.withPropertyValues("spring.cache.type=redis",
315334
"spring.cache.cacheNames[0]=foo",
316335
"spring.cache.cacheNames[1]=bar")
@@ -919,7 +938,7 @@ static class CouchbaseCacheAndCustomizersConfiguration {
919938

920939
@Configuration
921940
@EnableCaching
922-
static class RedisCacheConfiguration {
941+
static class RedisConfiguration {
923942

924943
@Bean
925944
public RedisConnectionFactory redisConnectionFactory() {
@@ -929,8 +948,22 @@ public RedisConnectionFactory redisConnectionFactory() {
929948
}
930949

931950
@Configuration
932-
@Import({ RedisCacheConfiguration.class, CacheManagerCustomizersConfiguration.class })
933-
static class RedisCacheAndCustomizersConfiguration {
951+
@Import(RedisConfiguration.class)
952+
static class RedisWithCacheConfigurationConfiguration {
953+
954+
@Bean
955+
public org.springframework.data.redis.cache.RedisCacheConfiguration customRedisCacheConfiguration() {
956+
return org.springframework.data.redis.cache.RedisCacheConfiguration
957+
.defaultCacheConfig()
958+
.entryTtl(java.time.Duration.ofSeconds(30))
959+
.prefixKeysWith("bar");
960+
}
961+
962+
}
963+
964+
@Configuration
965+
@Import({ RedisConfiguration.class, CacheManagerCustomizersConfiguration.class })
966+
static class RedisWithCustomizersConfiguration {
934967

935968
}
936969

spring-boot-project/spring-boot-docs/src/main/asciidoc/spring-boot-features.adoc

+4
Original file line numberDiff line numberDiff line change
@@ -4638,6 +4638,10 @@ key, Redis does not have overlapping keys and cannot return invalid values. We s
46384638
recommend keeping this setting enabled if you create your own `RedisCacheManager`.
46394639
====
46404640

4641+
TIP: You can take full control of the configuration by adding a `RedisCacheConfiguration`
4642+
`@Bean` of your own. This can be useful if you're looking for customizing the
4643+
serialization strategy.
4644+
46414645

46424646

46434647
[[boot-features-caching-provider-caffeine]]

0 commit comments

Comments
 (0)