메뉴

문서정보

목차

Docker Compose

Docker compose는 여러 컨테이너를 쉽게 실행 할 수 있도록 도와주는 도커 실행 툴이다. 이미지에서 컨테이너 하나 만들려면, 많은 옵션들을 설정해야 하는데, yaml 형식의 설정파일을 이용해서 여러개의 애플리케이션 서비스들을 효율적으로 관리 할 수 있다. 특히 Compose는 개발, 테스트, 스테이징 환경을 만드는데 많은 도움을 준다.

Compose는 3 단계로 사용 할 수 있다.
  1. 애플리케이션이 필요한 환경을 Dockerfile에 정의 한다.
  2. 애플리케이션 서비스를 위한 설정을 담고 있는 docker-compose.yml 파일을 만든다.
  3. docker-compose up명령을 실행하면 docker-compose.ymal 파일을 읽어서 컨테이너를 만든다.
docker-compose.yml 파일의 모습이다.
version: '3'
services:
  web:
    build: .
    ports:
    - "5000:5000"
    volumes:
    - .:/code
    - logvolume01:/var/log
    links:
    - redis
  redis:
    image: redis
volumes:
  logvolume01: {}
web과 redis 두개의 애플리케이션 서비스들에 대한 설정을 담고 있다. web의 경우 로컬에 있는 Dockerfile을 이용해서 이미지를 만든다. 이 웹 애플리케이션은 redis를 필요로 하는데 redis 이미지로 부터 컨테이너를 만들고 links를 이용해서 redis 컨테이너와 연결한다.

Compose 명령으로 할 수 있는 일들은 아래와 같다.

설치

우분투 리눅스에 설치했다.
# curl -L https://github.com/docker/compose/releases/download/1.13.0/docker-compose-`uname -s`-`uname -m` > /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose
docker-compose 버전을 확인해 보자.
$ docker-compose --version
docker-compose version 1.13.0, build 1719ceb

Flask Application 예제

Python Flask 웹 애플리케이션을 만들어 보자. 이 애플리케이션은 Python Flask와 Redis로 구성된다.

프로젝트를 위한 디렉토리를 만든다.
$ mkdir composetest
$ cd composetest

app.py 파일을 만든다.
from flask import Flask
from redis import Redis

app = Flask(__name__)
redis = Redis(host='redis', port=6379)

@app.route('/')
def hello():
    count = redis.incr('hits')
    return 'Hello World! I have been seen {} times.\n'.format(count)

if __name__ == "__main__":
    app.run(host="0.0.0.0", debug=True)
이 애플리케이션은 redis:6379 포트로 접근한다. docker의 link를 기능을 이용해서 연결 할 수 있다. 애플리케이션을 실행하기 위해서는 flask와 redis python 패키지를 설치해야 한다. 이들 패키지 정보를 가지고 있는 requirements.txt파일을 만들었다.
flask
redis

Dockerfile을 만든다.
FROM python:3.4-alpine
ADD . /code
WORKDIR /code
RUN pip install -r requirements.txt
CMD ["python", "app.py"]
이제 compose 설정파일을 만든다.
# cat docker-compose.yml
version: '2'
services:
  web:
    build: .
    ports:
     - "5000:5000"
    volumes:
     - .:/code
    links:
    - redis
  redis:
    image: "redis:alpine"
webredis 두 개의 서비스를 만든다. web은 docker build를 이용해서 이미지를 새로 만든다. redis는 redis:alpine 이미지를 이용해서 만든다.
$ docker-compose  up
Building web
Step 1 : FROM python:3.4-alpine
3.4-alpine: Pulling from library/python
79650cf9cc01: Pull complete
581a2604819e: Pull complete
cbecf1ae8c88: Pull complete
이미지가 빌드 되고, 자동으로 두개의 컨테이너가 만들어진다. 확인해 보자.
$ docker ps
CONTAINER ID  IMAGE             COMMAND                 CREATED             STATUS             PORTS                   NAMES
8f3c9c8bb7aa  composetest_web   "python app.py"         About a minute ago  Up About a minute  0.0.0.0:5000->5000/tcp  composetest_web_1
279f69da15e0  redis:alpine      "docker-entrypoint.sh"  About a minute ago  Up About a minute  6379/tcp                composetest_redis_1
Flask 애플리케이션이 redis를 잘 사용하고 있는지 확인해 보자.
$ curl localhost:5000
Hello World! I have been seen 5 times.
$ curl localhost:5000
Hello World! I have been seen 6 times.
카운트가 잘 올라가는 걸 보면 redis 연동까지 잘 된 것 같다.

스케일링

scale 옵션을 이용해서, 컨테이너 갯수를 설정 할 수 있다. 3개의 web 컨테이너와 1개의 redis 컨테이너를 구성해보자.
$ docker-compose scale web=3 redis=1
Starting composetest_web_1 ... 
Starting composetest_web_2 ... 
Starting composetest_web_3 ... 
Starting composetest_web_1 ... done
Starting composetest_web_2 ... done
Starting composetest_web_3 ... done
Creating composetest_redis_1 ... 
Creating composetest_redis_1 ... done
3개의 web 컨테이너를 확인 할 수 있을 것이다. 설정파일은 아래와 같이 수정했다.
version: '2'
services:
    web:
        build: .
        volumes:
            - .:/code
        links:
            - redis
    redis:
        image: "redis:alpine"
이렇게 구성하기 위해서는 앞단에 로드밸런서나 프락시 서버를 둬야 할 것이다. traefik 문서를 참고하자.

어디에 활용 할 수 있을까

개발 환경

소프트웨어를 개발과 테스트 그리고 배포의 일관성을 위해서, 개발 환경을 격리하는 건 매우 중요하다. compose 파일을 만들면, 소프트웨어를 구성하는 데이터베이스, 캐시, 웹 서비스를 하나로 통합할 수 있다. 이 compose 파일을 다른 개발자와 공유하면, 동일한 개발 환경을 만들 수 있다.

테스트 자동화

CD(Continuous Deployment) 또는 CI(Continuous Integration)에서 테스트는 매우 중요하다. 특히 MSA 환경에서는 다양한 서비스들이 API로 연결될 수 있기 때문에, 배포하려는 서비스 뿐만 아니라, 연동되는 다른 서비스들 까지도 함께 올려서 테스트를 해야 한다. Compose를 이용하면 테스트에 필요한 애플리케이션들을 동시에 띄워서 테스트 할 수 있다.

Single host deployments

일반적으로 compose는 개발과 테스트 영역에서 주로 사용했다. 실 서비스의 경우에는 서비스를 구성하는 컨테이너들이 원격으로 분리되기 마련인데, compose는 이런 기능을 가지고 있지는 않기 때문이다. 대신 swarm, mesos, k8s등의 다른 툴을 이용해서 배포한다. 하지만 다른 툴과 함께 조합해서 사용 할 수 있는 여지는 충분히 있다. mesos와 함께 사용한다고 가정해보자. 장황한 컨테이너 옵션을 설정하는 대신에, compose 파일을 실행하면 더 효율적으로 컨테이너를 관리 할 수 있을 것이다.