В настоящее время я настраиваю redis в приложении весенней загрузки, используя данные Spring. Все работает нормально, пока у меня нет двух одновременных запросов, что вызывает ClassCastException из внутреннего Jedis.
Это мой класс конфигурации:
@Configuration
@EnableRedisRepositories
public class RedisConfig {
@Bean
public RedisConnectionFactory redisConnectionFactory() {
RedisStandaloneConfiguration config = new RedisStandaloneConfiguration("ip", 6379);
config.setPassword("password");
JedisPoolConfig poolConfig = new JedisPoolConfig();
poolConfig.setTestWhileIdle(true);
poolConfig.setMinEvictableIdleTimeMillis(60000);
poolConfig.setTimeBetweenEvictionRunsMillis(30000);
poolConfig.setNumTestsPerEvictionRun(-1);
poolConfig.setMaxTotal(16);
return new JedisConnectionFactory(config, JedisClientConfiguration.builder()
.usePooling().poolConfig(poolConfig).build());
}
@Bean
public StringRedisConnection stringRedisConnection() throws Exception {
return new DefaultStringRedisConnection(redisConnectionFactory().getConnection());
}
}
Исключение:
org.springframework.data.redis.RedisSystemException: Unknown redis exception; nested exception is java.lang.ClassCastException: class [B cannot be cast to class java.lang.Long ([B and java.lang.Long are in module java.base of loader 'bootstrap')
at org.springframework.data.redis.FallbackExceptionTranslationStrategy.getFallback(FallbackExceptionTranslationStrategy.java:53) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.FallbackExceptionTranslationStrategy.translate(FallbackExceptionTranslationStrategy.java:43) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.connection.jedis.JedisConnection.convertJedisAccessException(JedisConnection.java:135) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.connection.jedis.JedisKeyCommands.exists(JedisKeyCommands.java:71) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.connection.DefaultedRedisConnection.exists(DefaultedRedisConnection.java:62) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.connection.DefaultStringRedisConnection.exists(DefaultStringRedisConnection.java:335) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
at org.springframework.data.redis.connection.DefaultStringRedisConnection.exists(DefaultStringRedisConnection.java:1889) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
... more frames and such
Caused by: java.lang.ClassCastException: class [B cannot be cast to class java.lang.Long ([B and java.lang.Long are in module java.base of loader 'bootstrap')
at redis.clients.jedis.Connection.getIntegerReply(Connection.java:260) ~[jedis-3.2.0.jar:na]
at redis.clients.jedis.BinaryJedis.exists(BinaryJedis.java:287) ~[jedis-3.2.0.jar:na]
at org.springframework.data.redis.connection.jedis.JedisKeyCommands.exists(JedisKeyCommands.java:69) ~[spring-data-redis-2.2.6.RELEASE.jar:2.2.6.RELEASE]
... 46 common frames omitted
Я использую это соединение на фильтре, чтобы проверить правильность токена.
Способ ввода соединения:
@Autowired
private StringRedisConnection redis;
onFilter() {
redis.exists("bla");
}
Что я делаю неправильно? Насколько я понимаю, Jedis не является поточно-ориентированным, но использует реализацию пула, что означает, что в моем параллельном сценарии у меня должно быть два соединения, но Spring возвращает одно соединение с помощью автопроводки.
Я также проверил другие вопросы:
Обновление: я прибил проблему к Джерси-на-Спринге. Похоже, причина в том, что бин stringRedisConnection
обрабатывается как бин с одной областью действия, а не как бин запроса (поэтому он получает соединение один раз и никогда после него). Похоже, причина в том, что бины в области запроса не существуют при использовании Jersey в SpringBoot ..