🐳 Docker 시리즈 살펴보기 🐳
      1. Docker와 Container
      2. Dockerfile과 Docker Image
➡️  3. Docker Volume
      4. Docker Network
      5. Docker Compose

 

 🐳 Docker Compose란?

  • 여러개의 컨테이너로부터 이루어진 서비스를 구축, 실행하는 순서를 관리할 수 있는 기능이며, YAML 파일로 작성된다.
  • 빌드 명령을 추가하면 docker compose는 DockerFile을 사용한다.
  • Docker compose는 앱이 실행되는 동안 컨테이너를 관리하는 역할을 한다.

 

다음은 docker-compose.yml 의 예시이다.

version: "3.9"  # 버전마다 지원 항목이 크게 다르기 때문에 필수 기재
services:
  web: # 서비스 이름
    build: .
    ports: # Dockerfile이 존재하는 위치
      - "8000:5000" # 공개할 포트를 설정한다. Host포트 : Container 포트 형식이다.
    volumes:
      - .:/code
      - logvolume01:/var/log
 
    depends_on:
      - redis # 컨테이너를 실행 할 순서를 설정한다.
  redis:
    image: redis # 이미지 이름
volumes:
  logvolume01: {} # 경로를 기입하지 않으면 도커가 임의로 경로를 설정한다.
  • compose V1 버전에서는 'docker-compose' 로 시작하는 명령어를 쓰지만, V2 부터는 'docker compose' 를 사용한다.

 

🐳 docker-compose 항목

  • version 3.x의 경우에 docker-compose.yml 을 구성하는 top-level 항목에는 version, services, volumes, networks 총 네가지가 있다.
명령어 설명
version docker compose 버전을 명시한다. 버전에 따라 형식이 다르기 때문에 버전에 맞춰 작성해야 한다.
services 실행하려는 서비스들을 기술. 서비스에 대한 옵션 설정
volumes 지정하려는 볼륨에 대한 정보
networks 컨테이너별로 개별적으로 네트워크를 구성한다. networks 를 정의하지 않으면 _default 라는 이름이 붙게되며, bridge 네트워크로 설정되어 기본적으로 컨테이너간 통신이 가능하다.
커스텀 네트워크로 설정할 수 있다.

 

각 컨테이너에 적용될 생성 옵션을 지정하는 services 의 하위 항목들 ( 이 외에도 많이 있다. → 공식문서 )

명령어 설명
image 컨테이너를 생성하는 데 필요한 이미지. 이미 존재하거나 Docker Hub (업무망에서는 abis)에 존재하는 이미지이다.
build 이미지 대신 Dockerfile이 존재하는 경로를 기재한다.
extends 다른 YAML 파일이나 현재 YAML 파일에서 서비스 속성을 상속 받도록 설정한다. 
command 컨테이너가 실행될 때 수행할 명령어를 설정한다. docker run 명령어의 마지막에 붙는 커맨드와 같다. Dockerfile의 RUN과 같은 배열 형태로도 사용할 수 있다.
volumes 컨테이너에 연결할 볼륨을 정의한다.
environment 서비스 내부 환경 변수 설정이다.
depends_on
서비스 간의 종속성을 의미하며 먼저 실행해야 하는 서비스를 지정하여 순서를 지정한다. 이 옵션에 지정된 서비스가 먼저 시작된다.
links도 depends_on과 같이 컨테이너의 생성 순서와 실행 순서를 정의하지만 depends_on은 서비스 이름으로만 접근할 수 있다는 점이 다르다.
  • 주의할 것은, depends_on 은 작 순서만 제어할 뿐, 컨테이너 안의 서비스가 "ready"(실행 가능한 상태) 가 되는 순서까진 보장하지 않는다는 것이다.
  • 컨테이너 내의 서비스의 실행 가능한 상태를 제어하려면 depends_on 이나 link 가 아닌 다른 방법을 취해야 한다 (stackoverflow)
  • 예를들어, DB가 생성되기 전에 SQL 쿼리를 날리면 안되므로, healthcheck등의 옵션을 통해 db 서비스가 올라간 것을 확인한 후, 다른 앱의 컨테이너를 실행하도록 할 수 있다
port 서비스의 컨테이너를 개방할 포트를 설정한다. docker run의 -p 옵션과 동일하다.
restart 재시작 옵션이다.  default는 'no'로, 재시작 하지 않는다.
  • no: 재시작 하지 않는다.
  • always: 항상 재시작한다.
  • on-failure: on-failure 에러코드와 함께 컨테이너가 멈추었을때만 재시작 한다.
  • unless-stopped: 개발자가 임의로 멈추려고 할때 빼고는 항상 재시작한다.

 

볼륨을 정의할 때 옵션을 지정하는 volumes의 하위 항목들 ( 공식문서 )

명령어 설명
driver 볼륨을 생성할 때 사용될 드라이버를 설정한다. 어떠한 설정도 하지 않으면 local로 설정되며, 사용하는 드라이버에 따라 변경해야 한다. 드라이버를 사용하기 위한 추가 옵션은 하위 항목인 driver_opts 로 설정한다.
external docker compose는 YAML 파일에서 volume, volume-from 옵션 등을 사용하면 프로젝트 마다 볼륨을 생성한다. 이때 external 옵션을 설정하면 볼륨을 프로젝트를 생성할 때마다 매번 생성하지 않고 기존 볼륨을 사용한다.

 

네트워크 구성 시 설정하는 networks의 하위 항목들 ( 공식문서 )

명령어 설명
driver docker compose는 기본적으로 bridge 타입의 네트워크를 생성하나, driver 항목을 정의하면 bridge 네트워크가 아닌 다른 네트워크를 사용할 수 있도록 해준다. 특정 드라이버에 필요한 옵션은 driver_ops 로 정의한다.
ipam IPAM (IP Address Manager)를 위해 사용할 수 있는 옵션이다. subnet, ip 범위 등을 설정할 수 있다.
external YAML 파일을 통해 프로젝트를 생성할 때마다 네트워크를 생성하는 것이 아닌, 기존의 네트워크를 사용하도록 설정한다.

 

🐳 사용법

$ docker compose [명령어] [옵션] # Docker compose V2 부터는 docker-compose 가 아닌 docker compsoe 로 사용한다.
  • docker compose 명령은 docker-compose.yml 을 저장한 디렉토리에서 실행된다. 다른 장소에 놓아두거나, 파일이름이 docker-compose.yml 이 아닐경우 -f 옵션으로 경로를 지정한다.

 

docker compose 의 주요 서브 명령어는 다음과 같다. 

서브 명령어
설명
up
컨테이너 생성+시작
down
docker compose up 실행했을때 만들어진 네트워크, 볼륨, 이미지 등의 리소스 삭제
start 컨테이너 시작
run 컨테이너 실행
stop
컨테이너 삭제
pause
컨테이너 일시 정지
unpause
컨테이너 재개
ps
컨테이너 목록 조회 (docker ps 와 유사하지만, docker compose ps는 docker-compose 파일과 관련된 컨테이너만 표시한다.)
port 공개 포트 조회
rm 컨테이너 삭제
logs 컨테이너 로그 출력
kill 실행중인 컨테이너 강제 정지
config 구성 확인

 

up / run / start 의 차이

  • up : docker-compose.yml 에 정의된 서비스들을 start 하거나 restart 한다.
  • run : 실행할 때, 서비스 명을 기입해야 하며 그 서비스와 depends_on 으로 명시된 서비스들만 실행된다.
  • start : restart 할때 사용된다. 컨테이너가 만들어졌지만 stop 되었을때 사용한다.

stop / down 차이

  • stop : 컨테이너 정지
  • down : 컨테이너와 networks를 정지 및 삭제

 

docker compose 의 서브 명령어에도 옵션을 주어 세부적인 설정이 가능하다. 가장 많이 사용되는 up 의 옵션들은 다음과 같다.

옵션 설명
-d 백그라운드에서 실행 (detached 모드로 실행) / 기본적으로는 attached 모드이다.
--build 이미지 빌드 / 기존에 있는 이미지를 사용하는 것이 아니라 새로 이미지를 빌드해서 컨테이너를 생성해야 할 때 사용한다. dockerfile을 사용할 수도 있다.
--no-build 이미지를 빌드하지 않을 때 사용한다.
-t , --timeout 컨테이너의 타임아웃을 초로 지정 (기본 10초) 할 때 사용한다.
-scale SERVICE=서비스 수 로드밸런싱을 위한 scale 설정을 한다. 기입한 숫자만큼의 복제본이 생기며, 이중 하나만 시작된다.