Redis
인메모리 데이터 저장소 Redis, 왜 사용할까? # Redis 파헤치기
레디스(Redis)는 언제 어떻게 사용하는 게 좋을까
Redis 란?
- 레디스 (Redis) 는 고성능 key-value 저장소로서 리스트∙해시∙셋∙정렬된 셋 등 여러 형식의 자료구조를 지원하는 NoSQL
- 메모리에 상주하면서 RDBMS 의 캐시 솔루션으로서 주로 사용되는 검증된 오픈소스 솔루션
Redis 사용 용도
- 레디스는 Message Queue, Shared Memory, Remote Dictionary 용도로 사용할 수 있음
- 특히 Remote Dictionary 로서 RDBMS 의 캐시 솔루션으로 사용 용도가 굉장히 높음
- RDBMS 에서 SELECT 쿼리문을 날려 특정 데이터들을 FETCH 했을 때 RDBMS 의 구조상 디스크에서 데이터를 꺼내오는데 메모리에서 읽어들이는 것보다 천 배 가량 더 느리기 때문
- 이 때 레디스 같은 유연한 자료구조를 가지는 인메모리 Key-value 솔루션을 사용하여 DB 부하의 Read 연산의 부하를 분산시키는 데 적용하는 것은 효율적인 처리
Tip! 인메모리 (In-Memory)
- 인메모리란 컴퓨터의 메인 메모리 RAM 에 데이터를 올려서 사용하는 방법을 말함
- 왜 메모리에 데이터를 올릴까?
- 이유는 명확하게도 속도 때문
- SSD 나 HDD 같은 저장공간에서 데이터를 가져오는 것보다 RAM 에 올려진 데이터를 가져오는데 걸리는 속도가 수백배 (HDD 기준) 이상 빠름
Redis 특징
- Key-Value Store
- 레디스는 거대한 맵 (Map) 데이터 저장소
- Key 와 Value 가 매핑된 단순한 맵 데이터 저장소로서 데이터를 레디스에 쉽고 편하게 읽고 쓸 수 있음
- 장점은 익히기 쉽고 직관적인 데 있고 단점은 Key-value 형태로 저장된 데이터를 레디스 자체 내에서 처리하는 것이 어렵다는 점
- Data Type
- Key 로 참조되는 Value 타입을 다양하게 지정하여 저장할 수 있음
- List, String, Set, Sorted set 등 여러 데이터를 저정하여 손쉽고 편리하게 데이터를 저장할 수 있음
- Persistence
- 레디스는 데이터를 디스크에 저장할 수 있음
- 따라서 레디스는 서버가 shutdown 된 후에 restart 하더라도 디스크에 저장해놓은 데이터를 다시 읽어서 데이터가 유실되지 않음
- 데이터를 디스크에 저장하는 방식은 Snapshot, AOF 방식이 있음
- Snapshot: 스냅샷은 RDB에서도 사용하고 있는 어떤 특정 시점의 데이터를 디스크에 옮겨담는 방식
- AOF : 레디스의 모든 write / update 연산 자체를 모두 log 파일에 기록하는 형태로 서버가 재시작할 때 write / update를 순차적으로 재실행하여 데이터를 복구
- 레디스 공식문서에서의 권장사항은 RDBMS의 rollback 시스템 같이 두 방식을 혼용해서 사용하는 것
- 주기적으로 Snapshot 으로 백업하고 다음 Snapshot 까지의 저장을 AOF 방식으로 수행
- ANSI C
- C언어로 작성되어 Java 와 같이 가상머신 위에서 동작하는 언어에서 발생하는 성능 문제에 대해 자유로움
- 곧바로 기계어로 동작하지 않고 어떤 가상의 머신 위에서 인터프리터된 언어로 가동하는 경우에는 가비지컬렉션 (Garbage Collection) 동작에 따른 성능 문제가 발생할 수 밖에 없는데 C언어로 작성된 레디스는 이런 이슈에 대해 자유로움
Cache
- 캐시란 자주 사용하는 데이터나 값을 미리 복사해 놓는 임시 장소를 말함
- 캐시에 있는 데이터는 시간과 자원 면에서 최소한의 비용으로 반복적으로 접근 할 수 있으며 캐시는 크게 두가지로 나눌 수 있음
- 레디스는 Global Cache에 적합함
Local Cache
- Local 장비 내에서만 사용 되는 캐시
- Local 장비의 Resource를 이용 (Memory, Disk)
- Local에서 작동 되기 때문에 속도가 빠름
- Local에서만 작동되기 때문에 다른 서버와 데이터 공유가 어려움
Global Cache
- 여러 서버에서 Cache Server에 접근하여 사용하는 캐시
- 데이터를 분산하여 저장 할 수 있음
- Replication: 데이터를 복제
- Sharding: 데이터를 분산하여 저장
- Local Cache 에 비해 상대적으로 느림 (네트워크 트래픽)
- 별도의 Cache Server를 이용하기 때문에 서버 간 데이터 공유가 쉬움
Redis 데이터 구조
- 레디스는 key-value 형태의 데이터를 저장소
- 즉, key 하나당 value를 저장하는 형태
- 레디스는 단순히 string 뿐만 아니라 다음과 같은 다양한 종료의 데이터 구조를 지원
- 레디스 데이터 구조
- 문자열 (string)
- 거의 대부분의 데이터를 문자열로 표현
- 가령 숫자나 날짜 및 시간 등을 문자열로 저장
- 해시 (hashes)
- 해시는 필드를 가질 수 있음
- 예를 들어 사용자 정보라는 해시가 있다면 이메일과 닉네임을 가질 수 있음
- 해시는 전체를 가져오거나 개별 필드를 가져올 수 있음
- 리스트 (list)
- 리스트는 왼쪽이나 오른쪽에 엘리먼트를 추가할 수 있음
- 리스트 안의 데이터는 문자열만 가능
- 집합 (sets)
- 셋은 리스트와 유사한 특징을 보이지만 고유 값을 저장한다는 점에서 차이점 존재
- 고유 값이 이미 정해진 셋에는 고유 값에 해당하는 멤버를 생성할 수 없음
- 정렬된 집합 (sorted sets)
- 정렬을 통해 특정 기준 값에 들어온 데이터만 필터링 가능
Redis 유의 사항
- 레디스는 한 번 생성한 키를 선택적으로 삭제하기 어려움
- 특별한 조치를 하지 않으면 레디스의 키는 삭제가 아닌 보관이 되어 서버를 종료해다가 다시 켜도 상태가 유지됨
- 레디스 키를 삭제하는 방법은 크게 3가지
- ① 일괄 삭제
- FLUSHDB 명령어를 통해 모든 키를 파괴
- 복구가 불가능하며 보통 개발 수준에서 사용
- ② 일정 시간 이후 삭제
- 각각의 키를 저장할 때 셋에 저장해 특정 시간이나 조건에 따라 삭제하는 방법
- 이 방법은 실제 삭제를 사용한다기 보단 밀어내기를 한다고 이해할 수 있음
- 셋은 하나의 키에 대해 여러번 등록을 해도 하나의 데이터만 남게 됨
- 이러한 특징과 더불어 셋은 교집합∙차집합∙합집합 같은 기능을 제공
- 두 가지 특징을 활용해 교차되는 키만 남기거나 뺀 연산을 적용해 키를 삭제할 수 있음
- ③ 기만 만료 후 삭제
- 가장 많이 사용되는 방법
- 키를 추적할 필요도 없고 쉽게 관리할 수 있음
- 이 방식을 사용할 때는 key-value 를 SET 커맨드로 저장해 EXPIRE 커맨드로 기간 만료 시간을 정하는 방법을 사용
- 또는 레디스 버전 2.0.0 이상을 사용할 때 SETEX 커맨드를 사용하는 방법
- SETEX 방법은 SET 과 EXPIRE 를 합친 것과 같다고 보며 됨