단의 개발 블로그

Mongo DB란 본문

Database/Mongo

Mongo DB란

danso 2024. 8. 28. 16:59

탄생배경

대부분의 서비스에서 데이터 관리는 RDBMS가 중심이였다. 하지만 서비스 규모가 커짐에 따라 방대한 양의 데이터를 처리하는데 어려움이 생기게 됐고, 빠른 속도로 처리할 수 있는 DB의 필요성이 증가했다. 상용 DBMS를 사용하는 회사가 대규모 데이터를 처리하려면 하나의 테이블에서 저장되던 데이터를 수십 수백개의 서버로 나눠 처리해야 하는데 이때 라이선스 비용이 엄청 증가한다. 한때 MySQL의 BigTable이라는 기능을 활용해 처리 했지만 트랜잭션 처리 부분에서 문제가 있었다. 구글의 Spanner라는 분산 트랜잭션 논문을 시작으로 페북, 트위터, 링크드인 등 여러 큰 기업들이 NoSQL을 개발하기 시작했다. 이때 개발 된 것이 MongoDB인데, 2007년 클라우드 플랫폼 서비스를 제공하는 10gen으로 시작됐다. 2009년에 오픈소스로 전환됐으며 10gen의 주력 서비스 보다 더 많은 인기를 누리게 되서 주력 솔루션으로 변경됐다. 사명또한 2013년 MongoDB Inc로 변경했다.

 

라이선스

기본적인 기능은 모두 오픈소스로 관리한다. 별도의 비용없이 사용 가능하다. 필요 시 소스코드를 수정하여 커스터마이징 해서 사용도 가능한데 이를 커뮤티니 버전이라고 부른다. 만약 기술지원이나 기타 여러 응용 기능을 사용하려면 유로 라이선스를 사용할 수도 있다. MongoDB 공식 홈페이지에 나와있는 유료 서비스 기능은 아래 표와 같다.

지원 프로페셔널 엔터프라이즈
Cloud Manager Premium O O
kerberos & LPAP   O
Auditing   O
SNMP   O
Encrypted Storage Engine   O
In-Memory Storage Engine   O
MongoDB Compass O O
MongoDB Connector for Bl   O
On-Demand Training  
Support SLA 2시간 1시간
Support Availability 24시간 x 365일 24시간 x 365일
Emergency Patches    

꼭 유료를 구매하지 않더라도 무료로 Cloud Manager의 일부 기능을 일정 비용 지불하고 사용 가능하다.

기능 상세기능 표준 프리미엄
백업 Unlimited Restores O O
  Backup Pricing 2.5달러 /GB/ 월 1GB 무료 같음
모니터링 Data Retention Full Historical Data 같음
  Granularity 2분 같음
  Custom Alerting O O
  APM Integration O O
자동화 Database Creation O O
  Database Modification O O
  Zero Downtime Upgrades and Downgrades O O
  RESTful API O O
쿼리 최적화 Visual Query Profiler   O
  Index Suggestions   O
  Automated Rolling Index Builds   O

 

버전

배포되는 버전은 다른 서비스와 같이 메이저, 마이너, 패치 번호로 부여한다. 하지만 주의할 점으로는 마이너 버전의 홀수는 개발버전이며, 짝수가 릴리즈 버전이다. 만약 직접 빌드해서 사용하면 마이너 버전을 짝수로 사용해야 한다.

 

RDBMS(MySQL) 차이점

MongoDB RDBMS(MySQL)
데이터베이스 데이터베이스
컬렉션 테이블
도큐먼트 레코드
필드 컬럼
인덱스 인덱스
쿼리 결과로 cursor 반환 쿼리 결과로 record 반환
db.users.insert ({user_id : "abcd"}) INSERT INTO users (user_id) values("abcd")
db.users.update({age: {$gt : 10}}, {$set: {status : "a"}}) UPDATE users SET status = "a" WHERE age > 10
db.users.remove({user_id : "abcd"}) DELETE FROM users WHERE user_id = "abcd"
db.users.find({user_id : "abcd"}) SELECT * FROM users WHERE user_id = "abcd"

 

아키텍처

응용 프로그램은 각 프로그래밍 언어별로 적절한 드라이버를 이용해서 서버와 통신한다. 네트워크 모듈은 클라이언트 요청을 받아서 서버의 쿼리 프로세서로 전달한다. 쿼리 프로세서 모듈은 여러 과정을 거쳐 사용자 데이터를 지정된 스토리지 엔진으로 주고 받는다. 가장 아래에 위치한 스토리지 엔진은 사용자 데이터를 디스크에 저장하거나 디스크로 부터 읽어서 쿼리 프로세서 모듈로 전달한다. 

 

배포형태

단일서버, 복제, 샤딩된 구조 등 다양하게 배포하여 사용 가능하다. 먼저 단일 노드부터 살펴보자

단일노드

아무런 관리 컴포넌트가 필요하지 않다. RDBMS와 같은 방식이다. 직접 연결하게 되며 별도의 레플리카 셋을 가지지 않으므로 장애가 발생할 경우 서비스에 치명적이다. 이는 주로 개발서버에서 사용한다.

단일 레플리카 셋

해당 형태도 별도의 관리용 컴포넌트가 필요하지 않다. 추가로 서버가 필요하다. 특정 서버가 장애가 발생할 경우 복구를 위한 최소 단위이다. 항상 레플리카 셋으로 배포해야 하며 드라이버는 직접 접속하지만 단일 노드와 접속할 때와 달리 레플리카 셋 옵션을 사용해서 접속한다.

항상 프라이머리 노드와 1개 이상의 세컨드리 노드로 구성되며, 프라이머리 노드는 요청을 받아서 처리하고 세컨드리 노드는 변경된 내용을 전달 받아서 서로의 데이터를 동기화 한다. 읽기 요청의 경우 세컨드리 노드로도 요청할 수 있다. 노드 간 투표를 통해서 프라이머리 노드를 결정하므로 되도록 홀수 개의 노드로 구성하는 것이 좋다. 3대의 서버로 구축할 경우 낭비가 될 수 있으므로 이때는 아비터 모드로 실행시켜서 사용한다. 아비터 모드로 시작한 경우 하트비트만 주고 받으며 선출에만 참여한다. 하나의 레플리카 셋에 여러 개의 아바타가 존재할 수 있지만 정상적인 상태에서 하나 이상의 아비터는 필요하지 않다.

샤딩된 클러스터

샤딩된 클러스터 구조에서는 하나 이상의 레플리카 셋이 필요하다. 각 레플리카 셋은 자신의 파티션 데이터를 가진다. 각각의 레플리카 셋을 샤드라고 하는데 이 샤드의 설정은 컨피그 서버가 관리한다. 샤딩된 클러스터에서 드라이버는 라우터로 연결하고 라우터는 자동으로 컨피그 서버로 부터 각 샤드가 가지고 있는 메터 정보를 참조하여 쿼리를 실행하는 방식으로 동작한다. 라우터는 말 그대로 사용자의 요청을 받아 전달하는 역할을 수행하는 것이다.

 

 

참고

https://www.mongodb.com/docs/

https://www.aladin.co.kr/shop/wproduct.aspx?ItemId=131270659&start=slayer