CacheConfig 설정

// Cache를 Enable 해준다.
@EnableCaching  
@Configuration  
public class RedisCacheConfig {
 
// cacheManager 설정
@Bean  
public RedisCacheManager cacheManager(RedisConnectionFactory connectionFactory) {
	RedisCacheConfiguration configuration = RedisCacheConfiguration  
        .defaultCacheConfig()  
        // null을 캐싱할지  
        .disableCachingNullValues()  
        // 기본 캐싱 유지 시간(Time to live)  
        .entryTtl(Duration.ofSeconds(10))  
        // 캐시를 구분하는 접두사 설정  
        .computePrefixWith(CacheKeyPrefix.simple())  
        // 캐시에 저장할 값을 어떻게 직렬화 / 역직렬화 할것인지  
        .serializeValuesWith(  
                SerializationPair.fromSerializer(RedisSerializer.java())  
        );  
  
return RedisCacheManager
		.builder(connectionFactory)
		.cacheDefaults(configuration)
		.build();
}

직렬화 설정

  1. Redis의 기본 직렬화인 RedisSerialize를 사용한다.
// Serializable 추가한다.
public record CartResponseDto(  
    String id,  
    ...
    String description  
) implements Serializable
 
// RedisCacheManager 세팅
RedisCacheConfiguration configuration = RedisCacheConfiguration
...
.serializeValuesWith(  
    SerializationPair.fromSerializer(RedisSerializer.java())
 
  1. GenericJackson2JsonRedisSerializer 사용
// 아래와 같이 추가만 해주면 된다.
RedisCacheConfiguration configuration = RedisCacheConfiguration
...
.serializeValuesWith(  
    SerializationPair.fromSerializer(new GenericJackson2JsonRedisSerializer()));
 

Redis에 class Type이 같이 저장된다. 3. Jackson2JsonRedisSerializer를 사용해보자 위 라이브러리를 사용할 때에는 Class Type을 지정해줘야 하므로 CacheManager를 생성할 때 아래와 같이 지정을 해 준다.

ObjectMapper objectMapper = new ObjectMapper();  
Jackson2JsonRedisSerializer<CartResponseDto> serializer = new Jackson2JsonRedisSerializer<>(  
    objectMapper, CartResponseDto.class);  
  
// 설정 구성  
// Redis를 이용해서 Spring Cache를 사용할 때  
// Redis 관련 설정을 모아주는 클래스  
RedisCacheConfiguration configuration = RedisCacheConfiguration  
    ...
    // 캐시에 저장할 값을 어떻게 직렬화 / 역직렬화 할것인지  
    .serializeValuesWith(  
        SerializationPair.fromSerializer(serializer));

다만 모든 곳에서 같은 타입을 사용할 수 없으므로 아래와 같이 필요할 Class Type마다 CacheManager를 만들어 줄 수 있다.

@Bean  
@Qualifier("cartCacheManager")
 
@Bean  
@Primary  
@Qualifier("defaultCacheManager")

이후 Cache를 추상화 한 곳에서 cacheManager를 지정해줄 수 있다.

@Cacheable(cacheNames = "userCart", key = "args[0]", 
		   cacheManager = "cartCacheManager")

@Cacheable

  • 캐시가 데이터가 없는 경우
    • 해당 메서드를 처음 호출할 때 캐시에 값이 없으면, 기존 로직(즉, 실제 메서드)을 실행하여 데이터를 가져옵니다.
    • 실행된 결과 데이터를 캐시에 저장해 다음 호출에서 사용할 수 있도록 합니다
  • 캐시에 데이터가 있는 경우
    • 동일한 요청이 있을 때 캐시에서 데이터를 가져와 반환합니다.
    • 실제 메서드는 실행되지 않고, 캐시에 저장된 데이터를 바로 반환하여 성능을 최적화합니다.

파라미터들

cacheName(value)

  • 캐시의 이름을 지정할 때 사용한다.
  • value와 cacheName은 같은 역할을 하며 두 기능의 차이는 존재하지 않는다.
  • 이름을 명확하게 하기 위해서 cacheName이 뒤에 추가되었다고 한다.
// 내부 구현은 아래로 둘다 AliasFor로 이름을 지정하는 것을 확인할 수 있다.
@AliasFor("cacheNames")  
String[] value() default {};  
  
 @AliasFor("value")  
String[] cacheNames() default {};

key

@Cacheable(cacheNames = "userCart", key = "args[0]")  
public CartResponseDto findCartById(String userId) {
	...
}

위와 같이 캐시의 키를 지정해 줄 수 있다. 그러면 아래와 같이 키가 지정이 된다.

  • userCart::normal-test

CachePut

캐시를 업데이트 해준다. 즉 항상 메서드가 실행이 되며 캐시에 저장된 값을 특정 조건 없이 항상 새로운 값으로 갱신하는 역할을 합니다.

CacheEvict

메서드가 실행될 때 캐시의 내용이 제거 된다.

 
@CacheEvict(cacheNames = "userCart", key = "args[1]")
public CartResponseDto createCart(Long productId, String userId) {
	...
}
 

파라미터

allEntries

key 값은 무시 되며 cacheNames에 해당하는 모든 캐시가 삭제가 된다. 기본값은 false로 key도 포함된 캐시가 지워진다.