컨테이너를 단일 도커 호스트에 배치하는 것은 쉽다. 그러나 많은 트래픽을 처리하는 시스템들은 대개 여러 컨테이너가 각기 다른 호스트에 배치된다.
도터 스웜은 여러 도커 호스트를 클러스터로 묶어주는 컨테이너 오케스트레이션 도구의 한 종류다. 이런 컨테이너 오케스트레이션 도구 없이는 도커 호스트 여러 대를 사용하는 확장성 있는 애플리케이션을 만들기가 매우 어렵다. 어느 도커 호스트에 어떤 컨테이너를 배치해야 하는지, 서로 다른 호스트에 위치한 컨테이너 간의 통신은 어떻게 제어하는지 등의 조율을 오케스트레이션 도구 없이 하기 힘들다.
이름 | 역할 | 대응하는 명령어 |
컴포즈 | 여러 컨테이너로 구성된 도커 어플리케이션을 관리(주로 단일 호스트) | docker-compose |
스웜 | 클러스터 구축 및 관리(주로 멀티 호스트) | docker swarm |
서비스 | 스웜에서 클러스터 안의 서비스(컨테이너 하나 이상의 집합)를 관리 | docker service |
스택 | 스웜에서 여러 개의 서비스를 합한 전체 어플리케이션을 관리 | docker stack |
여러 대의 도커 호스트로 스웜 클러스터 구성하기
윈도우용/macOS용 도커를 설치하면 호스트가 1대뿐이므로 여러 대의 호스트를 갖추려면 클라우드 서비스 등을 사용해야 한다. 테스트를 위해서는 '도커 호스트 역할을 할 도커 컨테이너를 여러 개 실행하는 방법'인 도커 인 도커(Docker in Docker, dind)라는 기능을 사용해본다. 테스트에서 사용할 컨테이너는 다음 3 종류로 모두 합해 5개다.
- registry * 1 : 도커 레지스트리 역할을 할 컨테이너로, manager 및 worker 컨테이너가 사용하는 컨테이너다. dind환경에서는 외부 이미지를 dind 컨테이너 파일 시스템을 통해 사용할 수 없기 때문에, 외부 도커에 저장된 이미지를 먼저 registry 컨테이너에 등록했다가 여기서 manager 및 worker 컨테이너가 이미지를 받아가도록 한다.
- manager * 1 : 스웜 클러스터 전체를 제어하는 역할을 한다. 여러 대 실행되는 도커 호스트(worker)에 서비스가 담긴 컨테이너를 적절히 배치한다.
- worker * 3
docker-compose.yml 파일을 다음과 같이 작성한다. 위의 구조를 컴포즈로 정의한 것이다. 모든 manager 및 worker컨테이너는 registry 컨테이너에 의존한다. 또 도커 레지스트리에는 일반적으로 HTTPS를 사용하지만, 여기서는 HTTP를 사용하기 때문에 이 문제를 해결하기 위해 --insecure-registry registry:5000 값을 줘서 http로도 이미지를 내려받을 수 있게 한다.
version: "3"
services:
registry:
container_name: registry
image: registry:2.6
ports:
- 5000:5000
volumes:
- "./registry-data:/var/lib/registry"
manager:
container_name: manager
image: docker:18.05.0-ce-dind
privileged: true
tty: true
ports:
- 8000:80
- 9000:9000
depends_on:
- registry
expose:
- 3375
command: "--insecure-registry registry:5000"
volumes:
- "./stack:/stack"
worker01:
container_name: worker01
image: docker:18.05.0-ce-dind
privileged: true
tty: true
depends_on:
- manager
- registry
expose:
- 7946
- 7946/udp
- 4789/udp
command: "--insecure-registry registry:5000"
volumes:
- "./stack:/stack"
worker02:
container_name: worker02
image: docker:18.05.0-ce-dind
privileged: true
tty: true
depends_on:
- manager
- registry
expose:
- 7946
- 7946/udp
- 4789/udp
command: "--insecure-registry registry:5000"
worker03:
container_name: worker03
image: docker:18.05.0-ce-dind
privileged: true
tty: true
depends_on:
- manager
- registry
expose:
- 7946
- 7946/udp
- 4789/udp
command: "--insecure-registry registry:5000"
컴포즈를 실행하면 registry 컨테이너 1대, manager 컨테이너 1대, worker컨테이너가 01번부터 03번까지 3대 총 5대가 실행된다.
✘ bohyun ~/Desktop/Work/study/docker-study master ±
docker-compose up -d
WARNING: Found orphan containers (master, slave01) for this project. If you removed or renamed this service in your compose file, you can run this command with the --remove-orphans flag to clean it up.
Pulling registry (registry:2.6)...
2.6: Pulling from library/registry
486039affc0a: Pull complete
ba51a3b098e6: Pull complete
470e22cd431a: Pull complete
1048a0cdabb0: Pull complete
ca5aa9d06321: Pull complete
Digest: sha256:c4bdca23bab136d5b9ce7c06895ba54892ae6db0ebfc3a2f1ac413a470b17e47
Status: Downloaded newer image for registry:2.6
Pulling manager (docker:18.05.0-ce-dind)...
18.05.0-ce-dind: Pulling from library/docker
911c6d0c7995: Pull complete
aff9b9c51076: Pull complete
9500841639b7: Pull complete
7224669f3f31: Pull complete
0134575d2ad9: Pull complete
e7d8d8ae52f7: Pull complete
59aca5a093a6: Pull complete
20b8e97b3cda: Pull complete
fb591ac9922a: Pull complete
779ddcf362b3: Pull complete
Digest: sha256:b813c414ee36b8a2c44b45295698df6bdc3bdee4a435481dbb892e1b44e09d3b
Status: Downloaded newer image for docker:18.05.0-ce-dind
Creating registry ... done
Creating manager ... done
Creating worker02 ... done
Creating worker03 ... done
Creating worker01 ... done
bohyun ~/Desktop/Work/study/docker-study master ±
docker container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
ce8f7af60cff docker:18.05.0-ce-dind "dockerd-entrypoint.…" About a minute ago Up About a minute 2375/tcp, 4789/udp, 7946/tcp, 7946/udp worker03
760fa825ec6b docker:18.05.0-ce-dind "dockerd-entrypoint.…" About a minute ago Up About a minute 2375/tcp, 4789/udp, 7946/tcp, 7946/udp worker01
7e4ff2b8f9d5 docker:18.05.0-ce-dind "dockerd-entrypoint.…" About a minute ago Up About a minute 2375/tcp, 4789/udp, 7946/tcp, 7946/udp worker02
469231dcd4dc docker:18.05.0-ce-dind "dockerd-entrypoint.…" About a minute ago Up About a minute 2375/tcp, 3375/tcp, 0.0.0.0:9000->9000/tcp, :::9000->9000/tcp, 0.0.0.0:8000->80/tcp, :::8000->80/tcp manager
a50dd2f3575e registry:2.6 "/entrypoint.sh /etc…" About a minute ago Up About a minute 0.0.0.0:5000->5000/tcp, :::5000->5000/tcp registry
호스트에서 manager 컨테이너에 docker swarm init 명령을 실행해 스웜의 manager 역할을 맡긴다.
swarm init 명령이 성공하면 해당 도커 호스트는 매니저로 마킹되고 스웜 모드가 활성화된다. 이제 여러 대의 worker 컨테이너를 등록해 클러스터를 형성할 차례다. 앞에서 swarm init 명령을 실행할 때 join 토큰이 생성돼 표준 출력으로 출력됐다. 스웜 클러스터에 worker로 등록하려면 join 토큰이 필요 하다.
매니저와 워커끼리는 컴포즈로 생성한 기본 네트워크 위에서 실행되므로 서로 컨테이너 명으로 식별 가능하다.
docker container exec -it manager docker swarm init
Swarm initialized: current node (l7omjz98sql0b2b4tptlvmexw) is now a manager.
To add a worker to this swarm, run the following command:
docker swarm join --token SWMTKN-1-1ljvxz69jcqzlolcsoqk3qj8dp6axjustwkdnni9bsiu25u6q1-cp4ma6msyv5g1u1mftullhzer 172.20.0.3:2377
To add a manager to this swarm, run 'docker swarm join-token manager' and follow the instructions.
worker 컨테이너에서는 manager:2377에 대하여 join 토큰을 전송하면 된다.
bohyun ~/Desktop/Work/study/docker-study master ±
docker container exec -it worker01 docker swarm join \
> --token SWMTKN-1-1ljvxz69jcqzlolcsoqk3qj8dp6axjustwkdnni9bsiu25u6q1-cp4ma6msyv5g1u1mftullhzer manager:2377
This node joined a swarm as a worker.
bohyun ~/Desktop/Work/study/docker-study master ±
docker container exec -it worker02 docker swarm join \
--token SWMTKN-1-1ljvxz69jcqzlolcsoqk3qj8dp6axjustwkdnni9bsiu25u6q1-cp4ma6msyv5g1u1mftullhzer manager:2377
This node joined a swarm as a worker.
bohyun ~/Desktop/Work/study/docker-study master ±
docker container exec -it worker03 docker swarm join \
--token SWMTKN-1-1ljvxz69jcqzlolcsoqk3qj8dp6axjustwkdnni9bsiu25u6q1-cp4ma6msyv5g1u1mftullhzer manager:2377
This node joined a swarm as a worker.
그리고 스웜 클러스터의 상태를 확인해보자. manager에서 docker node ls를 실행하면 다음과 같이 출력된다.
bohyun ~/Desktop/Work/study/docker-study master ±
docker container exec -it manager docker node ls
ID HOSTNAME STATUS AVAILABILITY MANAGER STATUS ENGINE VERSION
8xnyye1ym5ka2qb4nembqm62p 7e4ff2b8f9d5 Ready Active 18.05.0-ce
9tdwny5m75l82dlvyusuv4xlx 760fa825ec6b Ready Active 18.05.0-ce
l7omjz98sql0b2b4tptlvmexw * 469231dcd4dc Ready Active Leader 18.05.0-ce
29bz5nzp54c4okutknt66u91t ce8f7af60cff Ready Active 18.05.0-ce
도커 레지스트리에 이미지 등록하기
도커 이미지는 앞서 빌드한 example/echo를 사용하기 위해 레지스트리에 먼저 등록한다. 먼저 다음과 같이 docker image tag 명령을 실행한다.
bohyun ~/Desktop/Work/study/docker-study master ±
docker image tag example/echo:latest localhost:5000/example/echo:latest
태그 포맷은 [레지스트리_호스트/]리포지토리명[:태그] 인데, 여기서 레지스트리_호스트는 이미지를 등록하거나 내려받는 레지스트리를 의미한다. 지금 만든 registry 컨테이너는 호스트에서 localhost:5000과 같이 접근할 수 있으므로 리포지토리명 앞에 이 주소를 붙였다. 아래 명령어로 컨테이너에 이미지를 등록한다.
bohyun ~/Desktop/Work/study/docker-study master ±
docker image push localhost:5000/example/echo:latest
docker image pull 명령어로 worker에서 이미지를 받는다.
docker container exec -it worker01 \
> docker image pull registry:5000/example/echo:latest
latest: Pulling from example/echo
55cbf04beb70: Pull complete
1607093a898c: Pull complete
9a8ea045c926: Pull complete
d4eee24d4dac: Pull complete
9c35c9787a2f: Pull complete
8b376bbb244f: Pull complete
0d4eafcc732a: Pull complete
186b06a99029: Pull complete
2a2033f8fdec: Pull complete
817cf70d5a43: Pull complete
Digest: sha256:dbdf912b346917e66c648688911624029f0fb3597c985bb1b6b1fd2f8f90f88b
Status: Downloaded newer image for registry:5000/example/echo:latest
호스트에서 본 레지스트리는 localhost:5000이었지만, worker01에서 보면 registry 라는 이름이므로 이름으로 선언한다.
이제 worker01 컨테이너에서 example/echo:latest 이미지를 사용할 준비가 끝났다.
다음 블로그 글에서는 서비스와 스택에 대하서 설명을 이어가겠습니다.
'클라우드 > 도커' 카테고리의 다른 글
서비스와 스택 (0) | 2021.11.29 |
---|---|
컨테이너 실전 구축 및 배포 (0) | 2021.10.31 |
도커 컴포즈로 여러 컨테이너 실행하기 (0) | 2021.10.30 |
도커 컨테이너 (0) | 2021.10.17 |
도커 이미지와 컨테이너 기본 개념과 실행 (0) | 2021.10.17 |