Redis 성능 최적화
Redis 성능 최적화는 느린 명령을 피하고, key 크기와 접근 집중을 관리하고, 네트워크 왕복을 줄이는 것에서 시작합니다.
용어
| 용어 | 의미 |
|---|---|
| 시간 복잡도 | 명령 실행 비용이 데이터 크기에 따라 어떻게 증가하는지 |
| O(1) | 데이터 크기와 거의 무관한 상수 시간 |
| O(log N) | 데이터가 늘어도 완만하게 증가 |
| O(N) | 원소 수에 비례해 증가 |
| Big Key | 한 key의 value나 컬렉션이 매우 큰 상태 |
| Hot Key | 특정 key에 요청이 과도하게 몰리는 상태 |
| Pipelining | 여러 명령을 한 번에 보내 RTT를 줄이는 방식 |
| Slow Log | 느린 Redis 명령 기록 |
| Latency Monitor | 지연 이벤트 관찰 기능 |
질문
Redis는 메모리라 항상 빠른가?
아닙니다. 큰 key 조회, 전체 scan, 느린 Lua, 네트워크 RTT, connection pool 부족, fork / AOF rewrite, swap이 있으면 느려질 수 있습니다.
명령어 시간 복잡도
| 복잡도 | 예시 | 특징 |
|---|---|---|
| O(1) | GET, SET, INCR, SISMEMBER |
빠른 기본 명령 |
| O(log N) | ZADD, ZRANK |
Sorted Set 기반 |
| O(N) | KEYS, SMEMBERS, HGETALL, LRANGE 0 -1 |
큰 데이터에서 위험 |
# 위험
KEYS *
SMEMBERS huge:set
HGETALL huge:hash
# 대안
SCAN 0 MATCH user:* COUNT 100
SSCAN huge:set 0 COUNT 100
HSCAN huge:hash 0 COUNT 100
Big Key
Big Key는 자주 접근하지 않아도 위험합니다. 한 번 조회하거나 삭제하는 순간 Redis가 오래 붙잡힐 수 있습니다.
| 예시 | 문제 |
|---|---|
| 수십 MB String | 네트워크와 event loop 점유 |
| 필드 수백만 Hash | HGETALL 위험 |
| 원소 수백만 Set | 삭제와 복제 지연 |
| 긴 List | 전체 조회 위험 |
대응은 key 분할, 페이지 단위 조회, UNLINK, 자료구조 재설계입니다.
Hot Key
Hot Key는 하나의 key에 요청이 몰려 특정 Redis 노드가 병목이 되는 문제입니다.
| 대응 | 설명 |
|---|---|
| local cache | 아주 짧은 로컬 캐시로 Redis 요청 감소 |
| key sharding | hot:key:0..N으로 나누어 부하 분산 |
| replica read | 읽기 트래픽 분산 |
| TTL 조정 | 반복 재생성 방지 |
Cluster를 사용해도 key 하나는 한 slot에 있으므로 hot key가 자동 분산되지는 않습니다.
Pipelining과 Batch
Pipelining은 여러 명령을 한 번에 보내 네트워크 왕복을 줄입니다.
| 장점 | 주의 |
|---|---|
| RTT 감소 | 한 번에 너무 많이 보내면 응답 지연과 메모리 증가 |
| 대량 처리 효율 | 실패 처리와 부분 성공 처리 필요 |
대량 삭제, 대량 적재는 batch 크기를 제한하고 모니터링하면서 수행합니다.
Client-side Caching
클라이언트 로컬 메모리에 Redis 결과를 잠깐 보관해 Redis 요청 자체를 줄입니다.
| 장점 | 주의 |
|---|---|
| 가장 빠름 | 서버 간 정합성 문제 |
| hot key 완화 | 무효화 전략 필요 |
짧은 TTL 설정, Pub/Sub 무효화, version key 조합으로 stale을 줄일 수 있습니다.
Slow Log와 Latency Monitor
| 도구 | 볼 것 |
|---|---|
SLOWLOG GET |
어떤 명령이 느렸는지 |
LATENCY DOCTOR |
지연 이벤트 원인 |
INFO commandstats |
명령별 호출 수와 비용 |
Network RTT와 Connection Pool
| 항목 | 최적화 |
|---|---|
| RTT | Redis와 애플리케이션을 같은 region/VPC에 배치 |
| connection pool | 인스턴스 수와 동시 요청량 기준으로 제한 |
| timeout | 너무 길면 장애 전파, 너무 짧으면 일시 지연에 취약 |
| retry | 지수 backoff와 제한 횟수 |
Value 크기 최적화
| 방법 | 효과 |
|---|---|
| 불필요 필드 제거 | 메모리와 네트워크 절약 |
| 압축 검토 | 네트워크 절약, CPU 비용 증가 |
| String JSON vs Hash 선택 | 조회·갱신 패턴에 맞춤 |
| 기간별 key 분리 | 삭제와 조회 범위 축소 |
베스트 프랙티스
| 권장 방식 | 이유 |
|---|---|
| O(N) 명령을 운영 경로에서 제거 | event loop blocking 방지 |
| key 크기 제한을 둠 | big key 예방 |
| hot key를 prefix/API 지표로 관찰 | 특정 노드 과부하 탐지 |
| pipeline batch 크기 제한 | Redis와 client 메모리 보호 |
| slowlog 알림 설정 | 장애 전조 조기 감지 |
| connection pool 과대 설정 금지 | Redis 연결 폭증 방지 |
실무에서는?
| 증상 | 먼저 볼 것 |
|---|---|
| Redis timeout | slowlog, latency, CPU, network |
| 특정 노드만 높음 | hot key, slot 분포 |
| 삭제 후 지연 | big key, DEL 사용 여부 |
| 배포 후 DB 부하 증가 | cache warming, hit ratio |
| 응답 p99 악화 | RTT, pool 대기, command latency |
관련 파일: - Key 설계와 데이터 관리 - 장애 대응과 트러블슈팅 - 모니터링과 보안