1. 데이터베이스의 구분
데이터베이스는 크게 SQL DB와 NoSQL DB로 나눌 수 있다.
SQL DB는 스키마 기반의 테이블 구조를 가지고 있으며 ACID 특성을 보장하며, 금융 시스템과 같이 데이터 무결성과 트랜잭션 관리가 중요한 경우 사용된다. 게다가 40년 넘게 사용되고 있는 만큼 높은 안정성과 신뢰성을 자랑한다. 하지만, NoSQL DB에 비해서 확장성과 샤딩이 어렵다는 단점이 있다. 반면에, NoSQL DB는 스키마가 유연하고 대규모 데이터 분산 저장 및 처리에 최적화되어 있으며, BASE 특성을 가집니다. 또한, 빅데이터 분석을 처리하는데 탁월하며, 확장성도 훨씬 좋다. 하지만, 각각 DB마다 다르겠지만 호환성, 자료 부족 등의 문제가 있다.
실제로 위 그래프처럼, SQL DB가 거의 메인이 되고, NoSQL DB는 보조용으로 많이 사용한다.
2. 데이터베이스 선택 시 고려해야 할 요소
1) 데이터의 구조
- 정형 데이터: 테이블 형태로 명확히 정의된 스키마를 요구하는 경우 관계형 데이터베이스(RDB)가 적합하다.
- 비정형/반정형 데이터: JSON, XML 등의 유연한 데이터 구조를 처리하려면 문서 기반 NoSQL DB를 고려해라.
2) 트랜잭션 요구 사항
- ACID 준수: 데이터 무결성과 일관성이 중요한 경우 관계형 DB를 선택해라.
- 속도 우선: 실시간 처리와 확장성이 더 중요하다면 NoSQL이나 인메모리 DB를 선택하는 것이 좋다.
3) 분석과 검색
- 복잡한 분석: 데이터 집계와 통합을 위한 데이터 웨어하우스가 유리하다.
- 빠른 검색: 텍스트 검색이나 추천 시스템에는 검색 엔진 데이터베이스를 활용해야 된다.
4) 개발 및 운영 환경
- 기존 기술 스택과의 호환성: 현재 사용하는 기술과 DB가 잘 맞아야 유지보수가 쉽다. (Framework가 해당 Client Library를 지원하는가 여부)
- 클라우드 환경: AWS, GCP, Azure와 같은 클라우드 서비스와 통합 가능한 DB를 고려해라.
위 4가지를 염두해두고 여러 DB 유형을 살펴보고 골라보자.
3. 데이터베이스 유형과 사용 사례
1) 관계형 데이터베이스 (RDB)
대표 DB: MySQL, PostgreSQL, Oracle, SQL Server, SQLite
적합한 사용 사례 : 금융 시스템, 전자상거래, 메인 비즈니스
역사와 전통의 RDB이다. 데이터를 테이블 형태로 저장하는 데이터베이스이며, 일관성과 무결성을 보장하고, 복잡한 쿼리를 효율적으로 처리할 수 있다. 또한, 오류 발생시 롤백도 가능하다. (트랜잭션) 해당 데이터베이스에서 데이트를 접근하기 위해서는 SQL이라는 특수한 언어를 사용해야 한다. 40년이 넘는 세월동안 쓰여진 만큼, 안정적이며 자료도 많다. 아마 일반적으로, 메인 비즈니스 DB로 RDB를 많이 사용할 것 이다. 하지만, 이것저것 고려할 점이 굉장히 많다. 예를 들어서, 데이터의 무결성을 위해 데이터 베이스를 정규화를 한다던지 (데이터베이스 정규화), 데이터베이스 구조 및 관계를 어떻게 지정할지, 데이터가 삭제됐을 때 연관된 데이터를 어떻게 처리할지 (SET Null, CASCADE 등), 데이터 베이스 확장을 어떻게 할지 (샤딩), 조회 성능 향상을 위해서 인덱싱을 어떻게 할지 등등... 고려할점이 굉장히 많고 이에 대한 이론도 많이 알아야된다.
※ 어떤 RDB를 골라야될까요?
RDB도 종류가 많아 고민이 많이 될 것 이다. 그래서 비교를 해보고자 한다.
Oracle
보안, 트랜잭션 처리, 성능, 병행 처리, 백업 및 복구 등 엄청난 강점을 가지고 있다. 그래서 많은 대규모 기업 시스템에서 선호하는 DB이다. 하지만, 비용이 장난아니게 비싸기 때문에 개인이 쓰는 것은 좋지 않다.
Microsoft SQL Server
Windows 플랫폼에 최적화된 DB이다. 리눅스, Docker 등 다양한 플랫폼과 호환이 가능하도록도 지원을 해주고 있다. 이것도 역시 개인 프로젝트에서 쓰기 적합한 DB는 아니다.
그럼 이제 개인 프로젝트에서 쓰기 좋은 DB로 남는 것은 (대규모 시스템에 부적합하다는 것은 아니지만) MySQL, SQlite, PostgreSQL이다.
SQLite
타 RDB에 비해서 설치, 사용이 매우 쉽고, 리소스 사용량도 매우 적다. DB의 세부적인 기능까진 아니더라도 왠만한 기본적인 RDB의 기능은 모두 지원한다. 또한, 타 RDB처럼 유지 관리 작업이 필요하지 않다. (ex: 서버 권한, 버전 관리, 백업, 마이그레이션, DBMS 업그레이드 등) 그렇다고, 성능이 그렇게 떨어지는 편도 아니다. 그래서 주로 IOT 기기, 휴대폰 앱 등에서 사용하는 RDB라고 생각하면 좋다. 실제 백엔드 서버에서 사용하기에는 "유지 관리 작업"이 없다는 점 때문에 개인적으로 고가용성, 보안 등을 유지하기엔느 부적합하다고 생각한다.
PostgreSQL vs MySQL
이제 많이 고민 하는 부분이 MySQL을 쓸 것인가와 PostgreSQL을 쓸 것 인가이다. 둘을 비교해보자.
MySQL : Oracle 재단에 의해 관리된. 오랫동안 쓰여왔기 때문에 안정적이고 관련 자료도 많다. 타 DBMS에 비해서 설정도 쉽고 세부 설정이 그렇게 많이 요구되지 않는다. 멀티 스레드 방식으로 작동하여 동시에 많은 연결을 처리할 수 있다는 장점을 가지고 있다. 즉, 읽기 작업에 적합하다. 성능도 PostgreSQL에 비해 조금 더 우월하다.
PostgreSQL : 엄청난 확장성을 자랑한다. 대표적으로 Vector DB로 사용할 수 있는 pgVector, 지리 연산에 최적화된 PostGIS, cron job을 쉽게 할 수 있는 pg_cron, NoSQL DB로 전환할 수 있는 플러그인 등등 확장성이 매우 좋다. 또한, 멀티 프로세스로 동작하며, 이는 각 연결이 독립된 메모리 공간을 가지고 동작하기 때문에 보다 안정적인 데이터 처리가 가능하다. 또한, 쓰기 작업과 복잡한 트랜잭션 처리에 더 강점을 가지고 있다.
최근 조사 결과, 개발자들이 제일 선호하는 DB는 SQLite와 PostgreSQL이라고 한다. 왜냐하면 전자는 사용의 편리함, 후자는 확장성 때문일 것이다. 특히, 위치 정보와 관련된 도메인 작업이 PostGIS라는 강력한 플러그인 덕분에 PostgreSQL을 택하게 된다. 개인적으로 나도 PostgreSQL을 선호한다. 하지만 이건 개인적인 의견이며, 프로젝트 특성에 따라 적절하게 선택하면 좋을 것 같다.
2) Document 데이터베이스
대표 DB: MongoDB, Couchbase
사용 사례 : 유연한 스키마의 데이터를 저장해야 할 때 (ex : 블로그 게시물, 기사, 제품 설명, SNS 등), 로그, 데이터 아카이빙, 채팅 등
Json 같은 문서 형식으로 저장하는 DB이다. RDB와 달리 굳이 어떤 데이터를 저장할지 사전에 정의해두지도 않고, 정규화를 하지도 않는다. 또한, 데이터 분산을 염두해두고 많은 DB이기 때문에 데이터 베이스 분산 처리를 매우 잘해준다. (다만, RDB에 비해서 데이터베이스 간 일관성이 떨어질 수 있다.)
참고로, 블로그 게시물을 예시로 들었긴 했는데, 이를 어떻게 저장할지는 본인 선택인 것 같다. 데이터 특성에 따라 다르기 때문이다.
위 사진은 내가 라프텔에 문의했던 내용이다. 사용자 리뷰 데이터를 어떤 방식으로 저장하고 있냐에 대한 질문이었다. 라프텔은 굳이 MongoDB를 사용하지 않고 RDB에 저장한다고 한다. 다만, MongoDB 자체가 러닝커브가 높고, 조인 기능이 끔찍하기 때문에 잘 고민하고 쓰는 것을 추천한다.
3) 컬럼 패밀리 데이터베이스
대표 DB: Apache Cassandra, HBase
사용사례 : 로그 데이터 저장, 대규모 분산 시스템 (ex: 실제 인스타그램 같이 대규모 서비스에서 사용합니다)
Table을 만들고, Row를 저장한다. 그런데 ROW마다 Column의 형식이 달라도 상관 없이 저장할 수 있다. 또한, 데이터베이스 정규화를 하지 않는다. 특히, 이 DB의 강점은 복제 및 분산처리를 굉장히 잘해준다. 그래서 대규모 데이터에 빠른 읽기/쓰기를 제공한다. 하지만, RDB에 비해서는 데이터 베이스 무결성이 떨어질 수 있다. 즉, RDB만큼의 정확성을 보장하지 못한다는 것이다. 또한, RDB에 비해서 더 많은 리소스를 요구한다. 뿐만 아니라, 데이터에 접근하기 위해서 SQL이 아닌 각 DB마다 요구하는 CQL같은 언어를 사용해야 된다. 따라서, 개인이 하는 프로젝트 규모에는 쓰기 적합하지 않다. 주로, 인스타그램 같이 굉장히 큰 서비스에서 빠르게 읽기를 하기 위해서 사용한다.
4) 그래프 데이터베이스
대표 DB: Neo4j, OrientDB, ArangoDB
사용 사례 : SNS에서 사용자 간의 친구 관계, 뱌이러스 전파 지도, 비행기 노선 등
데이터 간의 관계를 시각화하여 저장 및 검색하는데 유리한 DB이다. RDB가 관계형 데이터베이스라서 오... 관계를 잘 표현하는 구나 생각할 수 있는데, RDB의 R이 Relational이라고 행렬에서 쓰이는 Relation이라는 단어에서 기인했기 때문에, 관계를 잘 표현하는 것은 아니다.
어쨋든, 데이터 간의 관계에 대해서만 저장하고 싶을 때 해당 데이터베이스를 사용하면 된다. 데이터에 접근하기 위해서는 Graph Query Language라는 것을 사용해야 된다
5) 검색 엔진 데이터베이스
대표 DB: Elasticsearch, OpenSearch
사용 사례 : 자동 검색어 완성, 실시간 검색, 데이터 집계 및 분석, 검색어 오타 보정
우리가 자동 검색어 완성을 구현할 때, 매번 RDB에 Like 문으로 검색하면 Like는 Full-Scan 방식이기 때문에 엄청난 트래픽이 몰리고 부하가 걸려서 다운될 가능성이 높아진다. (특히, 한글 데이터일 경우 형태소 분석 단계가 추가로 들어가서 더더욱 부하를 많이 잡아먹는다.) 따라서, 이런 실시간성이 요구되는 서비스에서는 검색 엔진 데이터베이스를 사용하는 것이 좋다. 특유의 역색인 구조 덕분에 대규모 텍스트에 대하여 실시간에 가까운 검색 및 집계가 가능해진다. 또한, Fuzzy 쿼리등을 사용하며 검색어에 대해서 오타 보정도 잘해준다.
다만, 사용해보면 알겠지만 ELK 자체가 리소스를 굉장히 많이 잡아먹는다. 또한, 러닝커브가 굉장히 높다. 개인적으로 쿠버네티스 처음 배울 때 급의 벽을 느꼈다.
해당 내용과 관련해서는 내가 정리해둔 글이 있으니 참고 바란다.
7) Key-Value 데이터베이스
대표 DB: Redis, Memcached, PostgreSQL(with hstore plugin)
사용 사례: 세션 관리, 캐싱, 순위표, Refresh Token 저장
Key-Value 데이터베이스는 가장 단순한 형태의 데이터베이스로, 키(Key)와 값(Value)의 쌍으로 데이터를 저장한다. 또한, Redis와 Memcached는 In-Memory 기반 DB이기 때문에 데이터 처리 속도가 매우 빠르다. 그래서 일반적으로 서브용 DB로 많이 사용한다.
일반적으로 많이 사용하는 Redis를 예시로 들어보면 세션 관리, 캐싱, 순위표, Refresh Token 저장, 실시간 인기 급상승 검색어, 메시지 브로커, 영상 스트리밍, 로그인 기록 저장, 동시성 예방, API Rate Limiter 등등의 용도로 사용할 수 있다. 그래서 Redis 같은 경우는 많이 써보면서 이 상황에서 사용해봐야겠다라고 직접 감을 잡는 것이 좋다. 아래 글을 참고 바란다.
그렇다면, Redis와 Memcached의 차이는 무엇인가?
첫째, Redis는 싱글 스레드 기반으로 동작하는 반면, Memcached는 멀티스레드를 지원하여 멀티 프로세싱이 가능하다. 이를 통해 Memcached는 여러 CPU 코어를 활용할 수 있어 높은 동시성을 제공한다.
둘째, Redis는 다양한 데이터 구조를 지원합니다. 문자열(String), 리스트(List), 셋(Set), 해시(Hash), 정렬된 셋(Sorted Set) 등 여러 자료구조를 통해 복잡한 데이터 모델을 구현할 수 있습니다. 반면, Memcached는 단순한 키-값 저장소로, 모든 데이터를 문자열 형태로만 저장한다.
셋째, Redis는 다양한 용도로 사용할 수 있도록 여러 기능을 지원합니다. 예를 들어, Pub/Sub 메시징, 트랜잭션, Lua 스크립트 실행, TTL 설정 등을 통해 복잡한 애플리케이션 요구 사항을 충족시킬 수 있다.
넷째, Redis는 데이터 지속성을 지원한다. 스냅샷(RDB)과 AOF(Append-Only File) 로그를 통해 데이터를 디스크에 저장하여, 시스템 장애 시에도 데이터를 복구할 수 있다. 반면, Memcached는 데이터 지속성을 지원하지 않으며, 서버 재시작 시 모든 데이터가 삭제된다.
그래서 개인적인 생각인데, Redis와 Memcached의 선택 기준은 크게 두가지로 나뉠 수 있다고 생각한다. Redis의 여러 자료 구조 및 Pub/Sub이나 Lua 스크립트 실행 등 다양한 기능이 필요하다면 Redis, 아니라면 Memcached. 또한, 동시성 처리가 굉장히 중요한 캐싱 데이터일 경우 (남은 티켓 수와 같은 중요한 수치 데이터 등) 반드시 Redis, 동시성 고려가 필요하지 않아 캐싱 성능이 우선시 될 경우는 Memcahced를 사용하는 것이 좋다고 생각한다. 왜냐하면 싱글 스레드 vs 멀티 스레드이기 때문이다. 다만, Redis가 애초에 Memcached의 단점을 보완하고자 나온 기술이다. 따라서, 왠만하면 Redis를 쓰는 것이 좋다. 실제로, StackOverflow를 둘러보면 그냥 Redis를 쓸 것을 권하고 있다.
8) 벡터 데이터베이스
대표 DB: Pinecone, PostgreSQL(with pg_vecotr plugin), Weaviate
사용 사례 : AI 추천 시스템, 텍스트/이미지 검색, 유사도 검색, 머신러닝
벡터 데이터베이스는 고차원 데이터를 처리하기 위해 설계된 데이터베이스이다. 예를 들어, 문장의 의미를 벡터로 변환한 임베딩 데이터를 저장하고, 유사도 검색에 활용된다. 즉, AI와 머신러닝에서 주로 사용되는 데이터베이스 유형이다. 유사도 검색에 최적화되어 있으며, 대규모 데이터를 빠르게 처리할 수 있는 고성능 인덱싱 알고리즘을 지원한다. 이런 저장된 Vector DB를 바탕으로 FAISS같은 유사도 비교 라이브러리를 이용하여 백터들을 비교하고 처리한다.
- Pinecone: 벡터 데이터베이스로 검색 및 추천 시스템 구현에 특화되어 있으며, 고성능과 분산처리를 지원.
- Weaviate: AI/ML 워크로드에 맞게 설계된 벡터 데이터베이스. 벡터 검색과 함께 GraphQL 쿼리도 지원.
- PostgreSQL (with pg_vector): PostgreSQL의 플러그인을 통해 벡터 데이터를 다룰 수 있음. 범용 DB로 활용 가능.
9) 시계열 데이터베이스
대표 DB : Prometheus, InfluxDB, TimescaleDB(PostgreSQL의 확장)
사용 사례 : 타임 스탬프 중심의 데이터 처리, 모니터링 시스템, IOT 센서 데이터, 이벤트 로
시간 기반 데이터의 저장 및 분석에 특화된 데이터베이스이다. 타임스탬프 중심의 데이터 처리를 한다. 데이터는 타임스탬프를 중심으로 정렬되며, 시간에 따른 데이터 집계, 쿼리, 분석 기능이 뛰어나다.
10) 데이터 웨어하우스
대표 DB: Amazon Redshift, Google BigQuery, Snowflake, Apache Hive
데이터 웨어하우스로 데이터를 저장하는 공간이다. DB도 데이터를 저장하는 공간인데 DW는 무슨 차이가 있는가?라고 생각하면 최근 데이터 인프라 관점에선 데이터 분석은 DW에서 많이 진행한다. 데이터 웨어하우스는 데이터 분석, 집계 및 대규모 쿼리에 최적화된 설계되어있다.
'BackEnd > DB' 카테고리의 다른 글
[DB] ElasticSearch의 Suggest API (0) | 2024.11.21 |
---|---|
[DB] ElasticSearch의 Search API (1) | 2024.11.19 |
[DB] CSV 파일 데이터 DB에 업로드 (8) | 2024.11.13 |
[DB] ElasticSearch Index 설정과 텍스트 분석 (0) | 2024.11.08 |
[DB] Elastic Search의 기초 (9) | 2024.11.07 |