Closed leshalv closed 2 years ago
Registration timeouts are generally misconfigurations. You can check your config file. Or provide a minimal example.
Looking at the update log, it should be caused by refactoring RedisMessageListenerContainer
@leshalv RedisMessageListenerContainer
is part of Spring Data Redis which is managed as a separate project. Please open an issue with them. We can re-open this issue if it turns out that a change in Spring Boot is necessary to accommodate some changes in Spring Data Redis. If you open a Spring Data Redis issue, please take the time to provide a complete yet minimal sample that reproduces the problem.
Hello! I also experienced this by just upgrading the spring-boot-starter-parent to 2.7.0
org.springframework.context.ApplicationContextException: Failed to start bean 'springSessionRedisMessageListenerContainer'; nested exception is java.lang.IllegalStateException: Subscription registration timeout exceeded.
at org.springframework.context.support.DefaultLifecycleProcessor.doStart(DefaultLifecycleProcessor.java:181)
at org.springframework.context.support.DefaultLifecycleProcessor.access$200(DefaultLifecycleProcessor.java:54)
at org.springframework.context.support.DefaultLifecycleProcessor$LifecycleGroup.start(DefaultLifecycleProcessor.java:356)
at java.lang.Iterable.forEach(Iterable.java:75)
at org.springframework.context.support.DefaultLifecycleProcessor.startBeans(DefaultLifecycleProcessor.java:155)
at org.springframework.context.support.DefaultLifecycleProcessor.onRefresh(DefaultLifecycleProcessor.java:123)
at org.springframework.context.support.AbstractApplicationContext.finishRefresh(AbstractApplicationContext.java:935)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:586)
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:147)
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:734)
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:408)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:308)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1306)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1295)
at (omitted project)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.springframework.boot.loader.MainMethodRunner.run(MainMethodRunner.java:49)
at org.springframework.boot.loader.Launcher.launch(Launcher.java:108)
at org.springframework.boot.loader.Launcher.launch(Launcher.java:58)
at org.springframework.boot.loader.JarLauncher.main(JarLauncher.java:65)
Caused by: java.lang.IllegalStateException: Subscription registration timeout exceeded.
at org.springframework.data.redis.listener.RedisMessageListenerContainer.lazyListen(RedisMessageListenerContainer.java:274)
at org.springframework.data.redis.listener.RedisMessageListenerContainer.start(RedisMessageListenerContainer.java:248)
at org.springframework.context.support.DefaultLifecycleProcessor.doStart(DefaultLifecycleProcessor.java:178)
... 22 common frames omitted
Caused by: java.util.concurrent.TimeoutException: null
at java.util.concurrent.CompletableFuture.timedGet(CompletableFuture.java:1784)
at java.util.concurrent.CompletableFuture.get(CompletableFuture.java:1928)
at org.springframework.data.redis.listener.RedisMessageListenerContainer.lazyListen(RedisMessageListenerContainer.java:268)
... 24 common frames omitted
@sylvermeister Perhaps you can provide a minimal sample that both @mp911de and I have asked for. If you can, please comment on https://github.com/spring-projects/spring-session/issues/2098 attaching it or linking to it.
FWIW, when using the Lettuce driver, you can enable debug logging for the io.lettuce
category to capture what Redis commands are issued and what responses you receive. With Spring Data Redis 2.7, we rewrote RedisMessageListenerContainer
to await subscription confirmation from Redis to avoid race conditions.
Subscription registration timeout exceeded.
FWIW, when using the Lettuce driver, you can enable debug logging for the
io.lettuce
category to capture what Redis commands are issued and what responses you receive. With Spring Data Redis 2.7, we rewroteRedisMessageListenerContainer
to await subscription confirmation from Redis to avoid race conditions.
@mp911de could you give some more details about the rewrite? What does "await subscription confirmation" mean? I even increased to subscription timeout to crazy levels and it will always time out. Would be good to know what changes are required. I'm getting failures by just upgrading from 2.6.x to 2.7. EDIT: Found https://github.com/spring-projects/spring-data-commons/wiki/Spring-Data-2021.2-(Raj)-Release-Notes#revised-redismessagelistenercontainer
Need to update things
<dependency>
<groupId>org.redisson</groupId>
<artifactId>redisson-spring-boot-starter</artifactId>
<version>3.17.3</version>
</dependency>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.7.12</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Lazy;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.listener.PatternTopic;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.listener.adapter.MessageListenerAdapter;
import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import redis.clients.jedis.Jedis;
@Configuration
public class RedisConfig {
@Autowired
private ApplicationConfig applicationConfig;
@Autowired
@Lazy
private UserCoinHistoryRepository userCoinHistoryRepository;
@Autowired
@Lazy
private CoinTransactionFactory coinTransactionFactory;
@Autowired
private RedissonClient redissonClient;
@Autowired
@Lazy
private RedisTemplate < String, Object > redisTemplate;
@Bean
public RedisTemplate<String, Object> redisTemplateJedis(RedisConnectionFactory cf) {
RedisTemplate<String, Object> redisTemplateJedis = new RedisTemplate<String, Object>();
redisTemplateJedis.setConnectionFactory(cf);
redisTemplateJedis.setKeySerializer(new StringRedisSerializer());
redisTemplateJedis.setValueSerializer(new StringRedisSerializer());
redisTemplateJedis.setHashValueSerializer(new Jackson2JsonRedisSerializer<>(Object.class));
return redisTemplateJedis;
}
@Bean
public MessageListenerAdapter messageListenerAdapter() {
return new MessageListenerAdapter(new RedisKeyExpirationListener(userCoinHistoryRepository,coinTransactionFactory,redissonClient,redisTemplate));
}
/**
* Configures a RedisMessageListenerContainer bean that sets up a Redis message listener.
* This container listens for keyspace notifications on all keys that match the pattern "__key*__:*".
*
* @param connectionFactory the factory to establish Redis connections
* @param messageListenerAdapter the adapter that handles the messages received
* @return the configured RedisMessageListenerContainer
*/
@Bean
public RedisMessageListenerContainer redisMessageListenerContainer(RedisConnectionFactory connectionFactory,
MessageListenerAdapter messageListenerAdapter) {
RedisMessageListenerContainer container = new RedisMessageListenerContainer();
container.setConnectionFactory(connectionFactory);
container.addMessageListener(messageListenerAdapter, new PatternTopic("__key*__:*"));
return container;
}
@Bean
public Jedis jedisClient() {
return new Jedis(applicationConfig.getRedisServer(),applicationConfig.getRedisPort());
}
}
springboot 2.7.0
upgrade to springboot 2.7.0 Project could not be started