Skip to content

Commit 2f1f353

Browse files
committed
Add to RedisSessionProperties configuration-strategy property to configure ConfigureRedisAction.
see gh-16943
1 parent 75e45fd commit 2f1f353

File tree

3 files changed

+102
-1
lines changed

3 files changed

+102
-1
lines changed

spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/session/RedisSessionConfiguration.java

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,13 +22,17 @@
2222
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
2323
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
2424
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
25+
import org.springframework.boot.autoconfigure.session.RedisSessionProperties.ConfigurationStrategy;
2526
import org.springframework.boot.context.properties.EnableConfigurationProperties;
27+
import org.springframework.context.annotation.Bean;
2628
import org.springframework.context.annotation.Conditional;
2729
import org.springframework.context.annotation.Configuration;
2830
import org.springframework.data.redis.connection.RedisConnectionFactory;
2931
import org.springframework.data.redis.core.RedisTemplate;
3032
import org.springframework.session.SessionRepository;
3133
import org.springframework.session.data.redis.RedisOperationsSessionRepository;
34+
import org.springframework.session.data.redis.config.ConfigureNotifyKeyspaceEventsAction;
35+
import org.springframework.session.data.redis.config.ConfigureRedisAction;
3236
import org.springframework.session.data.redis.config.annotation.web.http.RedisHttpSessionConfiguration;
3337

3438
/**
@@ -62,6 +66,19 @@ public void customize(SessionProperties sessionProperties, RedisSessionPropertie
6266
setCleanupCron(redisSessionProperties.getCleanupCron());
6367
}
6468

69+
@Bean
70+
@ConditionalOnMissingBean
71+
public ConfigureRedisAction configureRedisAction(RedisSessionProperties redisSessionProperties) {
72+
ConfigurationStrategy strategy = redisSessionProperties.getConfigurationStrategy();
73+
if (strategy == ConfigurationStrategy.NOTIFY_KEYSPACE_EVENTS) {
74+
return new ConfigureNotifyKeyspaceEventsAction();
75+
}
76+
if (strategy == ConfigurationStrategy.NO_OP) {
77+
return ConfigureRedisAction.NO_OP;
78+
}
79+
throw new IllegalStateException("Strategy '" + strategy + "' is not supported.");
80+
}
81+
6582
}
6683

6784
}

spring-boot-project/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/session/RedisSessionProperties.java

Lines changed: 31 additions & 1 deletion
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-2019 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.
@@ -40,6 +40,11 @@ public class RedisSessionProperties {
4040
*/
4141
private RedisFlushMode flushMode = RedisFlushMode.ON_SAVE;
4242

43+
/**
44+
* Allows specifying a strategy for configuring and validating Redis.
45+
*/
46+
private ConfigurationStrategy configurationStrategy = ConfigurationStrategy.NOTIFY_KEYSPACE_EVENTS;
47+
4348
/**
4449
* Cron expression for expired session cleanup job.
4550
*/
@@ -69,4 +74,29 @@ public void setCleanupCron(String cleanupCron) {
6974
this.cleanupCron = cleanupCron;
7075
}
7176

77+
public ConfigurationStrategy getConfigurationStrategy() {
78+
return this.configurationStrategy;
79+
}
80+
81+
public void setConfigurationStrategy(ConfigurationStrategy configurationStrategy) {
82+
this.configurationStrategy = configurationStrategy;
83+
}
84+
85+
/**
86+
* Allows specifying a strategy for configuring and validating Redis.
87+
*/
88+
public enum ConfigurationStrategy {
89+
90+
/**
91+
* Do nothing.
92+
*/
93+
NO_OP,
94+
/**
95+
* Ensures that Redis Keyspace events for Generic commands and Expired events are
96+
* enabled.
97+
*/
98+
NOTIFY_KEYSPACE_EVENTS
99+
100+
}
101+
72102
}

spring-boot-project/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/session/SessionAutoConfigurationRedisTests.java

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@
1616

1717
package org.springframework.boot.autoconfigure.session;
1818

19+
import java.util.Map;
20+
1921
import org.junit.jupiter.api.Test;
2022
import org.testcontainers.junit.jupiter.Container;
2123

@@ -28,13 +30,18 @@
2830
import org.springframework.boot.test.context.runner.WebApplicationContextRunner;
2931
import org.springframework.boot.testsupport.testcontainers.DisabledWithoutDockerTestcontainers;
3032
import org.springframework.boot.testsupport.testcontainers.RedisContainer;
33+
import org.springframework.data.redis.connection.RedisConnection;
34+
import org.springframework.data.redis.connection.RedisConnectionFactory;
3135
import org.springframework.session.data.mongo.MongoOperationsSessionRepository;
3236
import org.springframework.session.data.redis.RedisFlushMode;
3337
import org.springframework.session.data.redis.RedisOperationsSessionRepository;
38+
import org.springframework.session.data.redis.config.ConfigureNotifyKeyspaceEventsAction;
39+
import org.springframework.session.data.redis.config.ConfigureRedisAction;
3440
import org.springframework.session.hazelcast.HazelcastSessionRepository;
3541
import org.springframework.session.jdbc.JdbcOperationsSessionRepository;
3642

3743
import static org.assertj.core.api.Assertions.assertThat;
44+
import static org.assertj.core.api.Assertions.entry;
3845

3946
/**
4047
* Redis specific tests for {@link SessionAutoConfiguration}.
@@ -81,6 +88,32 @@ void redisSessionStoreWithCustomizations() {
8188
.run(validateSpringSessionUsesRedis("foo:event:0:created:", RedisFlushMode.IMMEDIATE, "0 0 12 * * *"));
8289
}
8390

91+
@Test
92+
void redisSessionConfigureNoStrategy() {
93+
this.contextRunner.withConfiguration(AutoConfigurations.of(RedisAutoConfiguration.class))
94+
.withPropertyValues("spring.session.store-type=redis",
95+
"spring.session.redis.configuration-strategy=no_op",
96+
"spring.redis.port=" + redis.getMappedPort())
97+
.run(validateStrategy(ConfigureRedisAction.NO_OP.getClass()));
98+
}
99+
100+
@Test
101+
void redisSessionConfigureDefaultStrategy() {
102+
this.contextRunner.withConfiguration(AutoConfigurations.of(RedisAutoConfiguration.class))
103+
.withPropertyValues("spring.session.store-type=redis", "spring.redis.port=" + redis.getMappedPort())
104+
.run(validateStrategy(ConfigureNotifyKeyspaceEventsAction.class,
105+
entry("notify-keyspace-events", "gxE")));
106+
}
107+
108+
@Test
109+
void redisSessionConfigureCustomStrategy() {
110+
this.contextRunner.withConfiguration(AutoConfigurations.of(RedisAutoConfiguration.class))
111+
.withUserConfiguration(MaxEntriesRedisAction.class)
112+
.withPropertyValues("spring.session.store-type=redis", "spring.redis.port=" + redis.getMappedPort())
113+
.run(validateStrategy(MaxEntriesRedisAction.class, entry("set-max-intset-entries", "1024")));
114+
115+
}
116+
84117
private ContextConsumer<AssertableWebApplicationContext> validateSpringSessionUsesRedis(
85118
String sessionCreatedChannelPrefix, RedisFlushMode flushMode, String cleanupCron) {
86119
return (context) -> {
@@ -94,4 +127,25 @@ private ContextConsumer<AssertableWebApplicationContext> validateSpringSessionUs
94127
};
95128
}
96129

130+
private ContextConsumer<AssertableWebApplicationContext> validateStrategy(
131+
Class<? extends ConfigureRedisAction> actionClass, Map.Entry... values) {
132+
return (context) -> {
133+
assertThat(context).hasSingleBean(ConfigureRedisAction.class).hasSingleBean(RedisConnectionFactory.class);
134+
assertThat(context.getBean(ConfigureRedisAction.class)).isInstanceOf(actionClass);
135+
RedisConnection connection = context.getBean(RedisConnectionFactory.class).getConnection();
136+
if (values.length > 0) {
137+
assertThat(connection.getConfig("*")).contains(values);
138+
}
139+
};
140+
}
141+
142+
static class MaxEntriesRedisAction implements ConfigureRedisAction {
143+
144+
@Override
145+
public void configure(RedisConnection connection) {
146+
connection.setConfig("set-max-intset-entries", "1024");
147+
}
148+
149+
}
150+
97151
}

0 commit comments

Comments
 (0)