Caching 전략
💡 목적
시스템 아키텍처를 작성하면서 Cache Layer를 구성하면서 Caching 전략에 따라 시스템 구성및 서비스의 성능에 영향을 줄 수 있다.
그에 따라 Caching 전략을 확인하고 준비하는 시스템or 서비스에 맞는 Caching 전략을 세우자.
💡 정리
Overview
- 웹서비스 시스템 아키텍처를 고민하면서 다양한 부분에 대해서 고민하게 된다.
- Failover, HA, Fault tolerance 등등
- 하지만 기본적으로 많은 사용자에게 서비스를 제공함에 있어서 많은 트래픽에 대해서 대응하며 시스템 성능을 향상 할수 있는 부분이 시스템 아키텍처에서 캐시 계층의 추가와 서비스와 시스템에 맞는 캐싱 전략을 적용하는 것이다.
- 이미 많은 사람이 알고있지만 기본적인 몇가지 캐싱전략을 알아보자.
Cache-Aside
- 보통 가장 많이 사용되는 캐싱 전략이다.
- 캐시를 application과 DB 옆에 두어 필요할 때만 데이터를 캐시에서 로드하는 전략
- Look Aside, Lazy Loading 전략 등등과 같은 것이다.
- Cache는 Database에 직접 연결되지 않고, application이 주체가 된다.
- Aside에서 느끼겠지만 Cache는 별도관리되고, 의존성이 낮다.
기본적인 전략
- Application의 데이터 조회 지점은 Cache, DB를 모두이다.
- Application에서는 Cache를 먼저 조회
- Cache 데이터가 존재(Cache Hit) → 조회한 데이터로 사용자에게 데이터 제공
- Cache 데이터가 미존재(Cache Miss) → Application에서 원천 데이터 Storage에서 데이터 조회 → Cache에 데이터 적재 → 사용자에게 데이터 제공
UseCase
- 읽기가 많은 작업(read-heavy workloads)에 적합하다.
- Memcached와 Redis가 널리사용된다.
장/단점
장점
- 실제로 사용하는 데이터만 캐시하기 때문에 자원을 효율적으로 사용할수 있다.
- 모든 데이터를 캐시에 적재하여 사용하는것이 아닌 자주 호출되는 데이터에 대해서 적재
- 캐시 오류에 대해서 탄력적이다.
- 캐시가 문제가 생겨도 DB에서 데이터를 조회하기 때문에 캐시 클러스가 다운되도 시스템 전체의 오류로 전파되지 않는다.
- DB와 데이터 모델이 다를 수 있음.
- 이부분은 DB의 데이터 그대로 적재하는 것이 아니 요청에 따른 비지니스 처리후의 모습으로 적재하여 특정 기능 요청의 모습에 매핑하여 대응할 수 있다.
단점
- 캐시에 데이터가 없는경우는 응답 시간이 더 걸린다.
- DB 조회 → Cache 적재의 과정을 하므로
- 데이터 일관성이 깨질 수 있다.
- 캐시에서 데이터가 없을때만 DB에서 데이터를 조회하여 캐시에 적재하기 때문에
- 따라서 데이터 성격을 파악하여 적절한 TTL을 잡아 주어야한다. (동기화 문제가 중요하게 된다.)
- 적합하지 않은 UseCase
서비스의 기본적인 기능을 처리할때는 적합한 전략이였다. 위의 장접같은 부분때문에..
하지만 이벤트등 특히 선착순 이벤트 같이 특정시간동안 평소의 몇백배 트래픽이 몰리는 기능에서는 적합하지 않은 전략이다. (이러한 요구사항에서는 DB는 모든 데이터를 Cache에 올리고 모두 DB에 요청이 흘러 부하가 같지 않게 하여야 한다.)
Read-Through Cache
- application, cache, database를 inline으로 배치
- 캐시에 데이터가 누락된 경우 데이터 베이스에서 누락된 데이터를 조회하여 캐시에 채우고 application에 반환
- Cache Aside, read-through 모두 데이터를 lazing load한다. 즉, 데이터를 읽을때만 조회한다.
- Application은 Cache Aside와 달리 Cache만 바라본다.
- through에서 느끼겠지만 Cache가 주체(main data store)이다.
- 데이터 동기화 역할은 Cache에게 위임한다.
기본적인 전략
- Cache Aside와 비슷하다.
- Application에서는 Cache를 먼저 조회
- Cache 데이터가 존재(Cache Hit) → 조회한 데이터로 사용자에게 데이터 제공
- Cache 데이터가 미존재(Cache Miss) → Cache를 관리하는 곳에서 원천 데이터 Storage에서 데이터 조회 → Cache에 데이터 적재 → application에게 데이터 제공 → 사용자에게 데이터 제공
UseCase
- 읽기가 많은 작업(read-heavy workloads)에 적합하다.
- Cache Aside와 달리 Database의 데이터와 모습이 같다. (Cache가 데이터 적재의 주체이므로)
장/단점
장점
- Cache Aside와 마찬가지로 읽기 부하가 많은 작업에서 적합
단점
- 처음 요청은 무조건 Cache Miss가 발생된다.
- 따라서, Batch, Scheduler등을 통해 Cach에 미리 데이터를 적재하여 Cache를 warm-up 시키기도 한다.
Cache Aside 마지막에 이야기한 특정시간동한 대량의 트래픽으로 조회 처리되어야하는 이벤트등의 기능에서 사용하면 좋다.
미리 데이터를 Cache에 적재하여 읽기부하를 핸들링할 수 있다.
Write-Through Cache
- Read Through와 반대로 구성
- Data write를 하는 전략이다.
- Read Through과 동일하게 Cache가 주체가 된다.
기본적인 전략
- Cache가 주체가 되어 데이터를 Cache와 Database에 데이터를 write하는 것
- Application에서 write와 관련된 요청
- Cache를 관리하는 곳 Cache에게 write → Cahce에 데이터 적재후 Database에 데이터 write
- Write는 항상 Cache를 통해서만 이루어진다.
UseCase
- 데이터를 데이터베이스에 작성할 때마다 캐시에 데이터를 추가하거나 업데이트합니다. 이로 인해 캐시의 데이터는 항상 최신 상태로 유지할 수 있지만, 여러가지 단점이 있다.
장/단점
장점
- Cache , Database의 데이터가 항상 동기화 되어있다.
단점
- 사용하지 않는데이터도 Cache에 적재한다. → 리소스가 낭비
- 쓰기 지연 시간이 증가
Write-Through 캐시와 Read-Through 캐시를 함께 사용하면 Read-Through 캐시의 모든 이점을 얻을 수 있으며 데이터 일관성 보장도 얻을 수 있다.
- DynamoDB Accelerator (DAX)는 좋은 예이다.
Write-Around
- wrtie 요청시 Cache를 거치지 않고 데이터베이스에 기록되고, 읽는 데이커만 캐시에 저장하는 전략
- Around : 캐시가 주변에 있다.
기본적인 전략
- Application에서 write 요청인입
- Database에서 write 요청
- Application에서 read 요청인입
- Cache 데이터가 존재(Cache Hit) → 조회한 데이터로 사용자에게 데이터 제공
- Cache 데이터가 미존재(Cache Miss) → Cache를 관리하는 곳에서 원천 데이터 Storage에서 데이터 조회 → Cache에 데이터 적재 → application에게 데이터 제공 → 사용자에게 데이터 제공
UseCase
- 기록하는 데이터가 자주 사용되지 않는 경우에 적합.
Write-Back(Write Behind)
- application에서는 cache에만 write 요청을 처리
- 별도의 서비스등(Batch, Scheduler등)을 통해 Database에 데이터를 동기화 시킨다.
기본적인 전략
- Application은 write 요청시 Cache에 요청 받은 데이터를 적재하고 요청에 대한 처리를 완료.
- 특정 서비스가 특정 주기로 Cache에 적재된 데이터를 Database에 적재한다.
UseCase
장/단점
장점
- 캐시 내용을 일정주기로 몰아서 Database에 적재하기 때문에 쓰기 비용을 절약한다.
단점
- 데이터를 모았다가 적재하므로 적재 주기 사이에 Cache가 문제가 발생할 경우 데이터 유실에 따른 문제가 발생할 수 있다.
아주 짧은 시간 대량의 트래픽으로 순식간에 처리해야하는 선착순 이벤트 같은 서비스의 경우 Read-Through와 Write-Back 전략을 이용하면 아주 유용한 아키텍처를 구성하여 이벤트를 처리할 수 있다.
💡 참고