VM을 이용한 MongoDB Replicaset 프로비저닝
카카오클라우드 VM을 이용하여 MongoDB Replicaset을 프로비저닝(provisioning)합니다. MongoDB Replicaset은 같은 Replicaset 그룹에 있는 MongoDB 프로세스에 대해 같은 데이터 집합을 유지하며, 중복성과 고가용성을 제공해 안정적으로 지속적인 서비스를 운영할 수 있습니다.
- 예상 소요 시간: 60분
- 사용자 환경
- 권장 운영 체제: MacOS, Ubuntu
- Region: kr-central-1, kr-central-2
리소스 계획
시나리오상에서 사용할 다양한 리소스의 리스트를 참고해 주세요.
가상 머신
인스턴스 이름 | 인스턴스 유형 | 볼륨 크기(GB) | 퍼블릭 IP | 이미지 |
---|---|---|---|---|
handson-bastion | m2a.large | 30 | Y | Ubuntu 20.04 |
handson-node-1 | m2a.large | 30 | N | Ubuntu 20.04 |
handson-node-2 | m2a.large | 30 | N | Ubuntu 20.04 |
handson-node-3 | m2a.large | 30 | N | Ubuntu 20.04 |
볼륨
볼륨 이름 | 연결할 인스턴스 | 크기(GB) |
---|---|---|
mongo-data-volume-1 | handson-node-1 | 500 |
mongo-data-volume-2 | handson-node-2 | 500 |
mongo-data-volume-3 | handson-node-3 | 500 |
보안 그룹
보안 그룹 이름 | 연결할 인스턴스 | 설명 |
---|---|---|
sg-mongodb | handson-node-1 handson-node-2 handson-node-3 | MongoDB 인스턴스에 적용할 보안 그룹 |
sg-bastion | handson-bastion | Bastion 호스트에 적용할 보안 그룹 |
보안 그룹별 인바운드 규칙
다음 버튼을 클릭하면 현재 사용 중인 나의 퍼블릭 IP를 확인할 수 있습니다.
보안 그룹 이름 | CIDR | 프로토콜 | 포트 | 역할 |
---|---|---|---|---|
sg-mongodb | SUBNET_CIDR | ICMP | ALL | ping-mongo |
sg-mongodb | BASTION_PRIVATE_IP/32 | TCP | 22 | ssh-mongo |
sg-mongodb | SUBNET_CIDR | TCP | 27017 | conn-mongo |
sg-bastion | {사용자 퍼블릭 IP}/32 | ICMP | ALL | ping-bastion |
sg-bastion | {사용자 퍼블릭 IP}/32 | TCP | 22 | ssh-bastion |
sg-bastion | {사용자 퍼블릭 IP}/32 | TCP | 81 | manage-bastion |
sg-bastion | {사용자 퍼블릭 IP}/32 | TCP | 10000-10010 | fowd-bastion |
Step 1. Bastion 호스트 생성하기
이 문서에서는 NGINX PROXY MANAGER를 이용하여 SSH 요청을 설정한 호스트에 포워딩하는 방법으로 Bastion 호스트를 구현합니다. Bastion 호스트를 생성하는 방법은 다음과 같습니다.
-
카카오클라우드 콘솔 > Virtual Machine에서 Bastion 호스트로 사용할 가상 머신을 생성합니다.
Bastion 호스트 생성 정보
Type Value Name handson-bastion Flavor m2a.large Image Ubuntu 20.04 Volume 30GB 보안 그룹 sg-bastion Floating IP Yes
sg-bastion의 인바운드 규칙
Bastion 호스트에 대한 보안 그룹 sg-bastion의 인바운드 규칙을 설정합니다.
보안 그룹명 CIDR 프로토콜 포트 역할 sg-bastion {사용자 퍼블릭 IP}/32
Icmp All ping sg-bastion {사용자 퍼블릭 IP}/32
TCP 22 ssh sg-bastion {사용자 퍼블릭 IP}/32
TCP 81 manage sg-bastion {사용자 퍼블릭 IP}/32
TCP 10000-10010 bastion -
터미널 실행 후 다음 명령어를 실행하여 Bastion 호스트에 SSH 접근합니다.
ssh -i ${KEYPAIR_NAME}.pem ubuntu@${BASTION_PUBLIC_IP}
-
터미널에 하단의 명령을 실행하여 Docker와 Docker compose 설치 및 NGINX PROXY MANAGER를 실행합니다.
curl -o install-bastion.sh https://raw.githubusercontent.com/kakaoenterprise/kc-handson-config/bastion-host/install-bastion.sh
bash install-bastion.sh -
브라우저에서
http://${BASTION_HOST_PUBLIC_IP}:81
주소를 입력하여 NGINX PROXY MANAGER 관리페이지에 접속할 수 있습니다. 접속을 위한 초기 계정 정보는 다음과 같습니다.구분 입력값 Email address admin@example.com Password changeme
Step 2. MongoDB 인스턴스 생성하기
카카오클라우드 콘솔 > Virtual Machine에서 MongoDB 인스턴스로 사용할 가상 머신을 생성합니다.
MongoDB 호스트 생성 정보
Type | Value |
---|---|
Name | handson-node |
Count | 3 |
Flavor | m2a.large |
Image | Ubuntu 20.04 |
Volume | 30GB |
보안 그룹 | sg-mongodb |
Floating IP | No |
보안 그룹 sg-mongodb의 인바운드 규칙
MongoDB 인스턴스에 대한 인바운드 규칙을 설정합니다.
보안 그룹 | CIDR | Protocol | Port |
---|---|---|---|
sg-mongodb | SUBNET_CIDR | ICMP | ALL |
sg-mongodb | BASTION_PRIVATE_IP/32 | TCP | 22 |
sg-mongodb | SUBNET_CIDR | TCP | 27017 |
Step 3. MongoDB 데이터 저장용 볼륨 생성하기
MongoDB 데이터를 저장할 별도의 볼륨을 사용하는 것을 권장합니다. MongoDB 데이터를 저장할 볼륨을 생성하는 방법은 다음과 같습니다.
-
카카오클라우드 콘솔 > Virtual Machine 에서 볼륨을 생성합니다.
MongoDB 호스트 정보
볼륨 이름 볼륨 유형 볼륨 크기 mongodb-data-volume-1 SSD 500
mongodb-data-volume-2 SSD 500
mongodb-data-volume-3 SSD 500
-
다음을 참고하여 인스턴스의 상세 페이지의 볼륨 탭에서 MongoDB 인스턴스에 연결할 볼륨을 선택합니다. (MongoDB 인스턴스에 생성한 볼륨을 추가합니다.)
인스턴스 볼륨 연결 정보 handson-node-1 mongodb-data-volume-1 handson-node-2 mongodb-data-volume-2 handson-node-3 mongodb-data-volume-3
Step 4. 포워딩 정보 업데이트하기
Bastion 호스트의 특정 포트에 접속하여 MongoDB 인스턴스에 ssh 접속할 수 있습니다. 이를 위해 Bastion 호스트의 특정 포트에 ssh 접속을 시도할 경우 해당 접속을 내부 특정 MongoDB 호스트에 포워딩하도록 설정합니다. Bastion 호스트의 포워딩 정보를 업데이트하는 방법은 다음과 같습니다.
-
브라우저에서
http://${BASTION_HOST_PUBLIC_IP}:81
주소를 입력하여 NGINX PROXY MANAGER 관리페이지에 접속합니다. -
NGINX PROXY MANAGER(관리 페이지) > Streams 탭에서 [Add Stream] 버튼을 클릭하여 Streams를 추가합니다.
- 내부 호스트를 추가 시 Bastion 호스트를 통해 내부 호스트로 접속할 수 있습니다.
Incoming Port Forward Host Forward Port 프로토콜 10000 handson-node-1_PRIVATE_IP 22 TCP 10001 handson-node-2_PRIVATE_IP 22 TCP 10002 handson-node-3_PRIVATE_IP 22 TCP -
Bastion 호스트의 포트를 통해 내부 MongoDB 인스턴스에 접근되는지 확인합니다.
ssh -i ${KEY_FILE} ubuntu@${BASTION_PUBLIC_IP} -p ${PORT}
예시: Bastion 호스트의 10000번 포트로 ssh 접속 시도 시 mongodb-node-1 인스턴스에 ssh 접속합니다.
ssh -i ~/hands-on.pem ubuntu@aaa.bbb.ccc.ddd -p 10000
Step 5. MongoDB 환경 구축하기
MongoDB를 설치하고 환경을 구축합니다. 이때 이전 단계에서 생성한 MongoDB 인스턴스에 ssh 접속하여 진행합니다.
DNS 설정하기
-
Replicaset을 관리하기 위해 인스턴스 IP 주소 대신 DNS 호스트 이름을 사용하여 도네임 이름을 정의합니다. 이때
/etc/hosts
파일을 수정하여 임의로 도메인 이름을 정의합니다.cat << EOF | sudo tee -a /etc/hosts
${HANDSON-NODE-1_PRIVATE_IP} node1.rs.in
${HANDSON-NODE-2_PRIVATE_IP} node2.rs.in
${HANDSON-NODE-3_PRIVATE_IP} node3.rs.in
EOF -
ping
명령을 실행하여 정의한 도메인 이름과 호스트가 일치하는지 확인합니다.ping node2.rs.in
# PING node2.rs.in (172.16.0.221) 56(84) bytes of data.
# 64 bytes from node2.rs.in (172.16.0.221): icmp_seq=1 ttl=64 time=2.18 ms
# 64 bytes from node2.rs.in (172.16.0.221): icmp_seq=2 ttl=64 time=0.752 ms
# ...
볼륨 마운트하기
데이터 및 로그를 저장하기 위해 생성한 볼륨을 데이터 디렉터리에 마운트합니다.
-
/dev/vdb
볼륨을 xfs 파일 시스템을 통해/data
데이터 디렉터리에 마운트합니다.cat <<EOF | sudo fdisk /dev/vdb
n
p
1
w
EOF
sudo mkfs -t xfs /dev/vdb1
sudo mkdir -p /data
sudo mount /dev/vdb1 /data -
볼륨이 데이터베이스의 데이터를 저장할 디렉터리에 마운트 되었는지 확인합니다.
df -h
# Filesystem Size Used Avail Use% Mounted on
# ...
# /dev/vdb1 500G 3.6G 497G 1% /data
# ...
MongoDB 설치하기
-
인스턴스에 MongoDB를 설치합니다.
sudo apt-get install gnupg
wget -qO - `HTTPS`://www.mongodb.org/static/pgp/server-6.0.asc | sudo apt-key add -
echo "deb [ arch=amd64,arm64 ] http://repo.mongodb.com/apt/ubuntu focal/mongodb-enterprise/6.0 multiverse" | sudo tee /etc/apt/sources.list.d/mongodb-enterprise.list
sudo apt-get update
sudo apt-get install -y mongodb-enterprise=6.0.3
sudo service mongod stop -
MongoDB의 데이터와 로그는 별도로 생성한 볼륨에 저장합니다. 데이터 및 로그를 저장할 디렉터리를 생성합니다.
sudo mkdir -p /data/mongodb
sudo mkdir -p /data/log/mongodb -
생성된 디렉터리에서 작업할 수 있도록 권한을 설정합니다.
sudo chown -R mongodb:mongodb /data/*
-
MongoDB 프로세스가 생성한 디렉터리에 정보를 저장하도록 값을 수정합니다.
/data/mongodb
에 데이터를 저장하고/data/log/mogodb/mongod.log
파일에 로그를 작성합니다.cat <<EOF | sudo tee /etc/mongod.conf
storage:
dbPath: /data/mongodb
systemLog:
destination: file
logAppend: true
path: /data/log/mongodb/mongod.log
net:
port: 27017
bindIp: 0.0.0.0
processManagement:
timeZoneInfo: /usr/share/zoneinfo
replication:
oplogSizeMB: 2000
replSetName: "handson-replicaset"
EOF -
MongoDB 프로세스를 시작합니다.
sudo service mongod start
Step 6. MongoDB Replicaset 배포하기
handson-node-1
, handson-node-2
, handson-node-3
인스턴스에 MongoDB 프로비저닝을 완료했다면, 인스턴스 중 한 노드에 접속하여 replicaset을 구축합니다.
-
handson-node-1
인스턴스에 접속하여 replicaset을 구축합니다.Replicaset 생성 (Remote - handson-node-1)mongosh --eval \
'rs.initiate( {
_id : "handson-replicaset",
members: [
{ _id: 0, host: "node1.rs.in:27017" },
{ _id: 1, host: "node2.rs.in:27017" },
{ _id: 2, host: "node3.rs.in:27017" }
]
})' -
handson-node-1
인스턴스에 생성된 replicaset의 설정을 확인합니다.replicaset 설정 확인mongosh --eval \
'rs.config()'