docker compose up을 실행하면 모든 서비스가 거의 동시에 뜬다. DB가 아직 준비되지 않았는데 앱이 먼저 연결을 시도하면 — 익숙한 ECONNREFUSED 에러다. depends_on은 이 시작 순서 문제를 선언적으로 해결하는 핵심 옵션이다.
services:
db:
image: postgres:16
app:
image: my-app
depends_on:
- db
이 설정은 db 컨테이너가 시작된 후 app을 띄운다. 단, "시작"은 프로세스가 실행됐다는 의미일 뿐, DB가 실제 쿼리를 받을 준비가 됐음을 뜻하지 않는다.
depends_on: Compose가 서비스 간 의존 관계를 추론해 시작 순서를 결정하는 옵션. 기본값은 condition: service_started.
db 컨테이너 시작
│
▼
healthcheck 실행 (반복)
│
healthy 상태?
No ──► 대기
Yes
│
▼
app 컨테이너 시작
condition 키를 쓰면 단순 시작 이상의 조건을 지정할 수 있다.
| condition | 의미 |
|---|---|
service_started | 컨테이너가 시작됨 (기본값) |
service_healthy | healthcheck가 통과됨 |
service_completed_successfully | 컨테이너가 exit 0으로 종료됨 |
service_healthy를 사용하려면 해당 서비스에 healthcheck가 정의돼 있어야 한다.
services:
db:
image: postgres:16
environment:
POSTGRES_PASSWORD: secret
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres"]
interval: 5s
timeout: 5s
retries: 5
app:
image: my-app
depends_on:
db:
condition: service_healthy
pg_isready: PostgreSQL이 연결 요청을 받을 수 있는 상태인지 확인하는 CLI 도구. exit code 0이면 healthcheck 통과.
healthcheck 없이 service_healthy를 쓰면 즉시 에러가 난다. Compose는 의존 대상 서비스에 healthcheck가 없으면 app 시작을 거부한다.
# 에러 예시
service "db" is not healthy
restart policy와 함께 쓸 것. service_healthy가 대기 중 타임아웃 되거나 DB가 재시작되면 앱도 같이 죽을 수 있다. restart: on-failure를 앱 서비스에 추가해두면 자동으로 재시도한다.
app:
image: my-app
restart: on-failure
depends_on:
db:
condition: service_healthy
depends_on은 런타임 의존성을 보장하지 않는다. 시작 시점에만 작동한다. DB가 이후에 재시작되면 앱은 이를 감지하지 못한다 — 앱 레벨의 재연결 로직(backoff retry)은 별도로 구현해야 한다.
여러 서비스를 동시에 기다릴 수 있다.
app:
depends_on:
db:
condition: service_healthy
redis:
condition: service_started
db는 healthy 상태를, redis는 단순 시작만 확인한 후 app이 뜬다.