1. Redis 활용시 직렬화/역직렬화를 해야하는 이유
직렬화/역직렬화는 자바객체 <-> 바이트/문자열 의 변환이다
Redis는 Json형식으로 바이트만 저장하기때문에 객체를 넣고 빼려면 이과정을 필수로 해주어야한다.
Redis는 바이트 저장소이기때문에
- 객체 -> 바이트(직렬화)
- 바이트 -> 객체 (역직렬화)
사람이 CLI(Command Line Interface)로 보기 좋게 하려면 문자열(JSON)으로 저장하는게 유리하다.
또한 포맷별(자바 기본직렬화 vs JSON)로 용량과 속도가 달라진다 .
1-1. 언제 어떤것을 직렬화하나?
- 키(Key) : 무조건 문자열! (StringRedisSerializer 사용)
키가 바이너리라면 CLI에서 깨진키로 보이고 디버깅 지옥을 맛볼수있다 - 값(Value) :
- 분산락값 : 보통 간단한 토큰 문자열(ex, UUID)는 JSON형식 필요없다.
- 캐시값 : DTO/List 같은 복합 객체 => JSON 직렬화 권장 (`ObjectMapper`사용)
- Sorted Set/Set/Hash : 스코어는 Double, 멤버는 String/JSON 등 명확히 결정해야한다 .
1-2. 직렬화 사용방법
- 키 : `StringRedisSerializer`
- 값(캐시/DTO) : `GenericJackson2JsonRedisSerializer`
(타입 정보를 JSON에 같이 넣어주기때문에 `List<PopularProductInfo>`와 같은 컬렉션도 복원이 쉽다)
* JdkSerializationRedisSerializer(자바 기본 직렬화)
-> 용량크고 언어간 비호환 , 클래스 변경취약 보안이슈로 권장하지않는다구한다..
2. 사용코드
2-1. 자바객체 -> JSON(직렬화)
String jsonString = objectMapper.writeValueAsString(myObject);
2-2. JSON -> 자바 객체 변환 (역직렬화)
ObjectMapper objectMapper = new ObjectMapper();
MyClass myObject = objectMapper.readValue(jsonString, MyClass.class);
* 주의사항
JSON필드와 자바 필드의 이름 일치 (매핑오류)
JSON의 데이터 형식이 올바른지 확인 -> 검증과정 추가하기도함
자바 객체필드가 private인 경우 Jackson이 해당 필드에 접근 가능하게 getter,setter를 제공해야함
JSON의 데이터구조가 복잡한경우 Jackson의 @JsonCreator , @JsonProperty 어노테이션 사용해서 생성자 주입을 통해 객체생성가능
3. 직렬화/역직렬화 예시
3-1. RedisTemplate + ObjectMapper
@Configuration
public class RedisConfig {
@Bean
public ObjectMapper objectMapper() {
return new ObjectMapper()
.findAndRegisterModules() // JavaTimeModule 등 자동 등록
.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS); // 날짜를 ISO 문자열로
}
@Bean
public RedisTemplate<String, Object> redisTemplate(
RedisConnectionFactory connectionFactory,
ObjectMapper objectMapper
) {
var template = new RedisTemplate<String, Object>();
template.setConnectionFactory(connectionFactory);
// 직렬화기
var keySer = StringRedisSerializer.UTF_8;
var valSer = new GenericJackson2JsonRedisSerializer(objectMapper);
// 키/값
template.setKeySerializer(keySer);
template.setValueSerializer(valSer);
// 해시용
template.setHashKeySerializer(keySer);
template.setHashValueSerializer(valSer);
template.afterPropertiesSet();
return template;
}
}
3-2. RedisCacheManager (스프링 캐시 어노테이션)
@Cacheable 값이 JSON으로 저장/복원된다.
GenericJackson2JsonRedisSerializer는 클래스 정보 포함이기때문에 리스트/맵도 역직렬화가 잘된당
@Bean
public RedisCacheManager cacheManager(RedisConnectionFactory cf, ObjectMapper om) {
var valSer = new GenericJackson2JsonRedisSerializer(om);
var config = RedisCacheConfiguration.defaultCacheConfig()
.entryTtl(Duration.ofHours(24))
.serializeKeysWith(RedisSerializationContext.SerializationPair.fromSerializer(StringRedisSerializer.UTF_8))
.serializeValuesWith(RedisSerializationContext.SerializationPair.fromSerializer(valSer));
return RedisCacheManager.builder(cf).cacheDefaults(config).build();
}'공부일기.. > Spring' 카테고리의 다른 글
| [Spring-legacy] 이거 @RequestBody Map으로 받아도 되나요? (1) | 2025.08.27 |
|---|---|
| [Redis] Redis 동작원리 : 속도 빠른이유 (4) | 2025.08.21 |
| Redis 캐시1 - RedisCacheManager (@Cacheable) 사용하기 (3) | 2025.08.16 |
| [Spring Boot] 게시판 만들기③ | EC2에 배포하고 실행까지 따라하기 (0) | 2025.07.06 |
| [Spring Boot 게시판 ] JWT 로그인 구현 하기 (0) | 2025.07.01 |