I'm using Redis as a cache storage in a Spring Boot 2 application. I'm using the @Cacheable annotation in some methods and I want to store the data in Redis as non-typed JSONs. With current my configuration, saving the data works fine but reading it is generating a ClassCastException.
All the solutions, answers, examples and tutorials use Jackson's ObjectMapper to configure either RedisTemplate or RedisCacheConfiguration adding a default typing attribute to the JSON. The thing here is this cache is going to be shared by different apps in different languages/technologies and I can't force the rest of the apps to work as Spring Boot does.
Here's what I have right now:
Config
@Bean
CacheManager cacheManager(RedisConnectionFactory connectionFactory) {
return RedisCacheManagerBuilder.fromConnectionFactory(connectionFactory)
.cacheDefaults(cacheConfiguration())
.build();
}
private RedisCacheConfiguration cacheConfiguration() {
return RedisCacheConfiguration.defaultCacheConfig()
.disableCachingNullValues()
.serializeKeysWith(SerializationPair.fromSerializer(RedisSerializer.string()))
.serializeValuesWith(SerializationPair.fromSerializer(new GenericJackson2JsonRedisSerializer(redisMapper())));
}
private ObjectMapper redisMapper() {
return new ObjectMapper()
//.enableDefaultTyping(DefaultTyping.NON_FINAL, As.PROPERTY)
.setSerializationInclusion(JsonInclude.Include.NON_EMPTY);
}
Service
@Cacheable(key = "'persons::' + #id")
public Person getPerson(Long id) {
// return person from DB
}
Result with the current config:
{
"name": "John",
"lastName": "Doe",
"age": 31
}
When Spring tries to read the content from the cache using the deserializers, it doesn't find a "@class" attribute with the type information so it returns a LinkedHashMap. After that the CacheInterceptor tries to convert the LinkedHashMap to a Person and there's when the ClassCastException occurs.
Request processing failed; nested exception is java.lang.ClassCastException: java.util.LinkedHashMap cannot be cast to com.test.dto.Person
At this point I'm OK if I need to write a serializer per type I want to store or maybe I can create a custom one for all. So far my research has been unsuccessful.
Thanks for your time.