Docker Compose로 멀티서비스 오케스트레이션

Source: raw/articles/2026-04-26-docker-compose-multi-service-orchestration.md Type: article By: Docker Official Docs + Real-world MLOps patterns Valid as of: 2026-04-26

핵심 Takeaway

  • Docker Compose: 여러 컨테이너 서비스를 단일 docker-compose.yml로 정의·실행
  • 서비스 순서 관리: depends_on + condition: service_healthy로 시작 순서 보장
  • 헬스체크: 각 서비스가 준비 완료 신호 → 다음 서비스 시작
  • 환경 분리: .env 파일로 개발/프로덕션 설정 관리
  • 데이터 지속성: Named volumes로 DB 데이터 영속화
  • 네트워크: Bridge network로 서비스 간 DNS 자동 해석
  • 실전 예: FastAPI(API) + PostgreSQL(DB) + Traefik(리버스프록시) 3서비스 통합
  • 검증: 한 명령(docker-compose up)으로 모든 서비스 정상 시작 확인

학습 목표 연계

Lecture Plan 20266-2: Docker Compose 멀티서비스 (Bloom L3-Apply)

학습목표증거상태
Behavior: 3개 서비스(FastAPI·DB·Traefik) 통합docker-compose.yml 실제 예제 + 설명
Condition: depends_on + 헬스체크로 순서 관리헬스체크 엔드포인트 + condition 문법
Degree: 한 번에 모든 서비스가 정상 시작운영 명령어 + 트러블슈팅 가이드

내용 구성

1. Docker Compose란 무엇인가

  • 정의: YAML 파일로 멀티컨테이너 애플리케이션 정의
  • 왜 필요: 수작업 docker run 명령 제거 → 일관성·재현성 보장
  • 언제 사용: 로컬 개발 + 소규모 운영 (Kubernetes 전 단계)

2. Compose 기본 구조

  • services: 각 컨테이너 정의 (API, DB, 프록시 등)
  • volumes: 데이터 지속성 (DB 스토리지)
  • networks: 서비스 간 통신 (기본: bridge)
  • environment: 환경 변수 (.env 파일 연결)

3. 핵심 1: Service 순서 관리 (depends_on + healthcheck)

  • 문제: PostgreSQL이 준비되기 전에 FastAPI가 시작 → 연결 실패
  • 해결 1: depends_on — 시작 순서만 정의 (준비 여부는 미보장)
  • 해결 2: condition: service_healthy — 헬스체크 + 순서 보장
  • 헬스체크 정의: FastAPI에서 /health 엔드포인트 → curl로 확인
  • PostgreSQL 헬스체크: pg_isready 명령어 사용

4. 핵심 2: 환경 변수 관리

  • .env 파일로 민감 정보 분리 (DB 비밀번호, API 키)
  • Compose에서 ${VARIABLE_NAME} 형식으로 참조
  • 개발/프로덕션 환경별 .env.dev, .env.prod 유지

5. 핵심 3: Volumes (데이터 지속성)

  • Named volumes: 컨테이너 재시작 시에도 데이터 유지
  • Bind mounts: 호스트 디렉토리와 동기화 (개발용)
  • PostgreSQL 예: volumes: - postgres_data:/var/lib/postgresql/data

6. 핵심 4: Networks (서비스 간 통신)

  • Bridge network 기본 생성 → 서비스명으로 DNS 자동 해석
  • FastAPI에서 "postgresql://db:5432/myapp" 형식으로 접속 가능
  • 서비스명 = hostname (별도 설정 불필요)

7. 실전 예제: FastAPI + PostgreSQL + Traefik

  • FastAPI (api): 포트 8000, /health + /predict 엔드포인트
  • PostgreSQL (db): 포트 5432, pg_isready 헬스체크
  • Traefik (proxy): 포트 80/443, HTTPS 리다이렉트, Let’s Encrypt 자동화
  • 통합 흐름: Traefik → FastAPI → PostgreSQL

8. 운영 명령어

  • docker-compose up -d: 백그라운드 시작
  • docker-compose ps: 서비스 상태 확인 (healthy/starting/unhealthy)
  • docker-compose logs -f api: 특정 서비스 로그 실시간 추적
  • docker-compose down: 모든 서비스 중지 + 컨테이너 제거
  • docker-compose down -v: 볼륨도 함께 제거 (주의!)

9. 트러블슈팅

  • 서비스가 unhealthy 상태: 헬스체크 엔드포인트 테스트 (curl http://localhost:8000/health)
  • 포트 충돌: docker-compose down 후 다시 시작
  • 데이터 손실: Named volumes 확인 (여부별로 docker volume ls)
  • 네트워크 통신 실패: 서비스명(hostname)이 네트워크 내 DNS 해석 가능한지 확인

10. 모범 사례 체크리스트

  • docker-compose.yml 버전 지정 (3.8 이상)
  • 모든 서비스에 healthcheck 정의?
  • condition: service_healthy 사용해 순서 보장?
  • .env 파일로 민감 정보 분리?
  • Named volumes 사용해 데이터 영속화?
  • 서비스명(hostname) 문서화?
  • 운영 명령어 README 기록?
  • 로컬 + 클라우드 환경 테스트?
  • 재시작 정책 설정? (restart: always)
  • 리소스 제한 설정? (memory, cpus)

관련 개념

모듈 6 다른 학습목표와의 연계

실전 구현 흐름

1단계: docker-compose.yml 작성

version: '3.8'
services:
  api:
    build: .
    ports:
      - "8000:8000"
    depends_on:
      db:
        condition: service_healthy
    healthcheck:
      test: ["CMD", "curl", "-f", "http://localhost:8000/health"]
      interval: 10s
      timeout: 5s
      retries: 3
    environment:
      DATABASE_URL: postgresql://${DB_USER}:${DB_PASSWORD}@db:5432/${DB_NAME}
  
  db:
    image: postgres:15-alpine
    environment:
      POSTGRES_USER: ${DB_USER}
      POSTGRES_PASSWORD: ${DB_PASSWORD}
      POSTGRES_DB: ${DB_NAME}
    volumes:
      - postgres_data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD", "pg_isready", "-U", "${DB_USER}"]
      interval: 10s
      timeout: 5s
      retries: 5
 
volumes:
  postgres_data:

2단계: .env 파일 작성

DB_USER=admin
DB_PASSWORD=secure_password_here
DB_NAME=myapp_db

3단계: 실행

docker-compose up -d
docker-compose ps  # healthy 확인
curl http://localhost:8000/health  # API 테스트

4단계: 검증

docker-compose logs -f api  # API 로그 확인
docker-compose exec db psql -U admin -d myapp_db -c "SELECT * FROM users;"  # DB 쿼리

성능·안정성 체크리스트

항목확인 방법목표
서비스 시작 시간docker-compose up 실행 시간< 30초
헬스체크 신뢰성서비스가 준비 완료 전 요청 차단 여부100% 차단
데이터 영속성docker-compose down 후 재시작 → 데이터 유지✅ 유지
네트워크 격리외부 호스트에서 내부 서비스 접근 불가✅ 격리

선행 개념

이 개념을 배우기 전에 필수로 알아야 할 것:

  1. Module 4-2 → fastapi-docker-official-deployment: 단일 FastAPI 컨테이너 Dockerfile 작성
    • 왜?: Docker Compose는 여러 컨테이너를 조율하는 것이므로, 먼저 단일 컨테이너를 이해해야 함
  2. Module 5 (파이프라인): 훈련된 ML 모델과 API 개념
    • 왜?: 실제 사례에서 FastAPI + PostgreSQL(DB) + Traefik(리버스프록시)을 함께 운영하기 때문

후속 개념 (이 개념이 선행)

이 개념을 배운 후 다음 단계:

  1. Module 6-3 → structured-logging-fastapi: Docker Compose 환경에서의 구조화된 로깅
    • 예: 여러 서비스의 로그를 docker-compose logs로 통합 모니터링
  2. Module 6-1 → fastapi-docker-traefik-ssl-production: Traefik을 Docker Compose와 함께 운영

마지막 체크

프로덕션 배포 전 반드시 확인:

  • docker-compose up으로 모든 서비스 정상 시작?
  • docker-compose ps에서 모든 서비스 healthy?
  • 로그에 오류 메시지 없음?
  • 데이터 지속성 테스트 완료? (재시작 후 확인)
  • 환경 변수(.env) 분리 완료?
  • 개발/프로덕션 환경 분리 계획?
  • 팀원이 docker-compose up 한 줄로 모든 환경 재현 가능?