컨테이너 하나만 띄울 때는 docker run 으로 충분하지만, 웹·DB·캐시처럼 여러 컨테이너를 함께 굴리면 명령이 금방 길어집니다. 이럴 때 쓰는 게 Docker Compose 예요. 여러 컨테이너를 하나의 정의 파일로 설정하고 관리합니다.
구성 요소
Compose 파일은 크게 세 가지로 나뉩니다.
- 서비스(Service): 애플리케이션을 이루는 각 컨테이너
- 네트워크(Network): 서비스 간 통신 설정
- 볼륨(Volume): 컨테이너와 호스트 간 데이터 공유
기본 명령어
docker compose build # 정의된 서비스 빌드
docker compose up -d # 모든 서비스 생성·시작 (-d 백그라운드)
docker compose down # 모든 서비스 중지 + 생성된 네트워크·볼륨 삭제
최신 Docker에는 Compose가 플러그인으로 들어와 있어
docker compose(띄어쓰기) 형태로 씁니다. 예전 독립 실행형은docker-compose(하이픈)였는데, 새 환경이라면 플러그인 방식을 권장합니다.
예시: Nginx + MySQL
services:
web:
image: nginx
ports:
- "80:80"
volumes:
- ./html:/usr/share/nginx/html
db:
image: mysql
environment:
MYSQL_ROOT_PASSWORD: example
volumes:
- db-data:/var/lib/mysql
volumes:
db-data:
예시: Jenkins
services:
jenkins:
container_name: jenkins
image: jenkins/jenkins:lts
ports:
- 8080:8080
- 50000:50000
volumes:
- ./jenkins_home:/var/jenkins_home
예시: 프라이빗 레지스트리
services:
registry:
restart: always
image: registry:2
container_name: registry
ports:
- 5000:5000
volumes:
- /root/registry/data:/var/lib/registry
무중단으로 정적 파일 교체하기
정적 파일을 서빙하는 컨테이너에서, 볼륨 안의 콘텐츠를 새 버전으로 바꿔야 할 때가 있습니다. rm -rf 로 지우고 새로 넣으면 삭제되는 동안 서비스가 끊기죠. 그래서 삭제 대신 빠른 mv 두 번으로 처리합니다.
# 1) 서비스 중인 파일 백업
cp -r app/build/site site_backup
# 2) 임시 폴더 준비
mkdir tmp
# 3) 기존 파일을 tmp로 옮기는 동시에, 새 파일을 서비스 폴더로 이동
mv app/build/site/* ./tmp && mv new/build/site/* app/build/site/
mv 는 같은 파일시스템 안에서는 사실상 즉시 끝나므로, 삭제하는 방식보다 서비스 중단 시간을 크게 줄일 수 있습니다. 문제가 생기면 백업으로 되돌리면 되고요.
Compose는 “이 서비스들이 이렇게 묶여서 돈다”를 파일로 남기는 도구입니다. 한 번 잘 정의해두면 up -d 한 줄로 환경이 재현되니, 손으로 여러 컨테이너를 관리하던 수고가 확 줄어듭니다.