개발일지/문제 해결
Caused by: com.fasterxml.jackson.databind.exc.InvalidDefinitionException: Java 8 date/time type `java.time.LocalDateTime` not supported by default: add Module "com.fasterxml.jackson.datatype:jackson-datatype-jsr310" to enable handling (through reference c
티에리앙리
2025. 3. 16. 19:58
Caused by: com.fasterxml.jackson.databind.exc.InvalidDefinitionException:
Java 8 date/time type `java.time.LocalDateTime` not supported by default:
add Module "com.fasterxml.jackson.datatype:jackson-datatype-jsr310" to enable handling
(through reference chain: com.example.springbootredis.model.User["createdAt"])
Spring Boot에서 Redis에 데이터를 저장할 때, Jackson을 사용하여 객체를 JSON으로 직렬화(Serialization)하는 과정에서 발생한 에러이다.
java.time.LocalDateTime 타입을 기본적으로 직렬화할 수 없어서 에러 발생했다.
기존 CacheServiceTest 코드에서
cachDataTest() 코드를 실행할때 이러한 에러가 발생한다.
@SpringBootTest
class CacheServiceTest {
@Autowired
private CacheService cacheService;
@Test
void cacheDataTest() {
// Given - 실행 준비
User user = new User(1L, "testUser", "test@example.com", LocalDateTime.now());
// When - 진행
cacheService.cacheData("user:1", user, 60);
Optional<User> cachedUser = cacheService.getCachedData("user:1", User.class);
// Then - 결과 검증
assertTrue(cachedUser.isPresent());
assertEquals(user.getUsername(), cachedUser.get().getUsername());
}
}
기존 RedisConfig 코드
@Configuration
public class RedisConfig {
@Bean
public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory connectionFactory) {
RedisTemplate<String, Object> template = new RedisTemplate<>();
template.setConnectionFactory(connectionFactory);
// Key Serializer 설정 - redis에 맞게 변환
template.setKeySerializer(new StringRedisSerializer());
// Value Serializer 설정 - redis에 맞게 변환
Jackson2JsonRedisSerializer<Object> serializer = new Jackson2JsonRedisSerializer<>(Object.class);
template.setValueSerializer(serializer);
template.setHashValueSerializer(serializer);
return template;
}
}
해당 코드에서
Jackson2JsonRedisSerializer 를 사용하는데 해당 Serializer Object Mapper에 설정이 빠졌다.
그러므로 직접 사용할 ObjectMapper를 설정한다.
이렇게 ObjectMapper 를 추가하면 테스트가 정상적으로 성공한다.
@Configuration
public class RedisConfig {
@Bean
public ObjectMapper objectMapper() {
ObjectMapper mapper = new ObjectMapper();
mapper.registerModule(new JavaTimeModule());
mapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
mapper.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
return mapper;
}
@Bean
public RedisTemplate<String, Object> redisTemplate(ObjectMapper mapper, RedisConnectionFactory connectionFactory) {
RedisTemplate<String, Object> template = new RedisTemplate<>();
template.setConnectionFactory(connectionFactory);
// Key Serializer 설정 - redis에 맞게 변환
template.setKeySerializer(new StringRedisSerializer());
// Value Serializer 설정 - redis에 맞게 변환
Jackson2JsonRedisSerializer<Object> serializer = new Jackson2JsonRedisSerializer<>(mapper, Object.class);
template.setValueSerializer(serializer);
template.setHashValueSerializer(serializer);
return template;
}
}