본문 바로가기

Backend/SpringBoot

SpringBoot로 캐싱(Caching)하기

안녕하세요!

이번 포스팅에서는 SpringBoot의 spring-boot-starter-cache를 이용해서

메소드에 캐싱을 추가해보도록 하겠습니다.

 

코드는 Github에서 확인이 가능합니다.

 

캐싱?

캐싱을 사용해보기 전에 간단하게 캐싱에 대해 정리하자면,

들어오는 값을 기억해뒀다가 추후에 같은 값이 들어오게 되면 메소드를 돌지 않고 바로 결과값을 내놓는 것을 의미합니다.

캐싱에 대한 정확한 의미는 이곳을 참조하시면 됩니다!

이런 상황에서 캐싱을 유용하게 사용할 수 있습니다.

  • 사용빈도가 높은 단순 반복 작업
  • 결과가 자주 변경되지 않는 데이터

사전준비

프로젝트 설명

제가 캐싱을 할 메소드는 특정 코드를 문자열 값으로 바꿔서 리턴해주는 메소드입니다.

S → "과자"

D → "음료수"

G → "껌"

이런 식으로 실제로 DB에서 코드 같은 축약된 값을 통해 다른 테이블에서 실제 값을 얻어오는 경우가 많았습니다. (제가 실제로 코드를 짤 땐) 이런경우에 캐싱을 사용하시면 성능이 많이 향상됩니다.

의존성 추가

build.gradle

compile('org.springframework.boot:spring-boot-starter-cache')

캐시를 사용하기 위해 의존성에 spring-boot-starter-cache를 추가해줍니다.


구현

Config 추가

CachingConfig.java

@Configuration
@EnableCaching
public class CachingConfig {

    @Bean
    public CacheManager cacheManager() {
        SimpleCacheManager cacheManager = new SimpleCacheManager();
        cacheManager.setCaches(Arrays.asList(
                new ConcurrentMapCache("product")));
        return cacheManager;
    }
}

CachingConfig를 추가해줍니다.

product는 후에 추가할 cash의 이름입니다.

만약 캐싱을 여러 곳에서 사용한다면

cacheManager.setCaches(Arrays.asList(
          new ConcurrentMapCache("캐시 이름"), 
          new ConcurrentMapCache("캐시 이름")));

이렇게 작성할 수 있습니다.

Test로 확인하면 더 깔끔하고 확실하게 짤 수 있을 것 같다고 생각했지만,

직관적으로 확인할 수 있는 방법으로 하는게 좋다고 생각하여 컨트롤러와 서비스를 분리해서 코드를 작성했습니다!

 

Service 추가

CashService.java

@Service
public class CashService {

    @Cacheable(value = "product")
    public String vendingMachine(char code){

        String output = "";

        System.out.println( code +  " product를 조회합니다 ...");

				// 각 코드에 맞는 결과물 리턴
        if(code == 'S'){
            output = "과자";
        }
        else if(code == 'D'){
            output = "음료수";
        }
        else if(code == 'G'){
            output = "껌";
        }

        return output;

    }
}

 

Controller 추가

CachingController.java

@RestController
public class CachingController {

    @Autowired
    CashService cashService;

    @GetMapping("/cache")
    public String test(){

        char[] productCode = {'S', 'D', 'G'}; // 상품 코드들
        Random random = new Random();

        for(int i=0; i<10; i++){
						// 랜덤으로 코드를 뽑아서 코드로 값을 바꿔주는 메소드 호출
            String output = cashService.vendingMachine(productCode[random.nextInt(3)]);

						// 결과 출력
            System.out.println(output + "출력합니다. ");
        }

        return "";
    }

}

테스트 코드를 짜고 돌린 후에

/cache 에 접속한 후에 콘솔을 보게 되면

캐싱이 되어서 조회 메소드를 나올 수 있는 모든 경우의 수인 3번밖에 조회를 하지 않는 것을 확인할 수 있습니다!

이런 식으로 정말 간단하게 캐싱을 사용할 수 있습니다.

Config를 만들지 않고도 어노테이션(@Cacheable, @EnableCaching)만으로 간단하게 사용을 할 수 있다고 하는데,

저는 설정 때문인지 실행오류가 나서 위의 방법을 사용했습니다.

감사합니다!


출처

A Guide To Caching in Spring | Baeldung