[IT-정보] 도커 컴포즈 정리 완벽 가이드 – 컨테이너 운영의 핵심과 실무 적용법

도커 컴포즈 기본 개념를 설명하는 완벽 정리 대표 이미지

왜 지금 도커 컴포즈의 개념을 확실히 잡아야 할까요

새로운 프로젝트를 시작하고 서버를 띄울 때를 떠올려 보세요. 데이터베이스를 실행하기 위해 docker run 명령어를 입력하고, 그 다음에 Redis를 띄우고, 또 웹 서버를 실행합니다. 이때 각 컨테이너를 서로 연결하기 위해 네트워크 옵션을 넣고, 볼륨을 연결하고, 환경 변수를 일일이 설정하다 보면 어느 순간 머릿속이 복잡해지기 시작해요.

명령어 한 줄이면 될 줄 알았던 작업이 어느새 수십 줄의 쉘 스크립트로 변해 있고, 팀원에게 서버 환경을 공유하려고 해도 “어떤 명령어를 어떤 순서로 쳤었지?”라며 당황하는 상황이 발생하곤 합니다. 이런 혼란은 단순한 실수를 넘어 서버 운영의 불안정성으로 이어질 수 있어요. 컨테이너가 하나라면 명령어로 충분하지만, 세 개가 넘어가기 시작하면 이야기는 완전히 달라집니다.

이런 문제를 해결해 주는 도구가 바로 도커 컴포즈(Docker Compose)예요. 여러 개의 컨테이너를 하나의 파일로 정의하고, 단 한 번의 명령어로 전체 시스템을 유기적으로 실행할 수 있게 도와줍니다. 도커 컴포즈를 제대로 이해한다는 것은 단순히 명령어를 외우는 것이 아니라, 복잡한 인프라를 하나의 설계도로 관리하는 법을 배운다는 뜻이에요.

이 글을 모두 읽고 나면 여러분은 다음과 같은 능력을 갖추게 될 거예요.

  • 복잡한 컨테이너 실행 과정을 하나의 설정 파일로 관리하는 법
  • docker-compose.yml 파일의 핵심 옵션을 완벽히 해석하는 능력
  • 실무에서 자주 발생하는 컨테이너 간 연결 및 설정 오류 해결법

자, 그럼 이제 복잡한 명령어의 늪에서 벗어나 설계도로 관리하는 스마트한 운영의 세계로 들어가 볼까요?

도커 컴포즈 시작 전 반드시 알아야 할 핵심 용어와 준비물

도커 컴포즈를 본격적으로 다루기 전에, 우리가 다룰 언어들을 먼저 정리해야 해요. 무작정 파일을 작성하다 보면 “이게 서비스인가, 컨테이너인가?” 하며 헷갈리는 순간이 반드시 오거든요. 도커 컴포즈는 도커 엔진 위에서 돌아가는 오케스트레이션 도구라는 점을 머릿속에 먼저 넣어두세요.

핵심 개념 3가지 정리

가장 먼저 구분해야 할 개념은 프로젝트, 서비스, 컨테이너예요. 이 관계를 명확히 이해해야 설정 파일의 구조가 눈에 들어옵니다.

  • 프로젝트(Project): 여러 서비스를 하나로 묶은 단위예요. 보통 docker-compose.yml 파일이 있는 디렉토리 이름을 기준으로 생성돼요.
  • 서비스(Service): 어떤 애플리케이션을 실행할 것인지에 대한 정의예요. 예를 들어 “MySQL 서비스”, “Web 서비스”처럼 역할을 나타내죠.
  • 컨테이너(Container): 서비스 정의를 바탕으로 실제로 실행된 실체예요. 하나의 서비스 정의로 여러 개의 컨테이너를 띄울 수도 있어요.
💡 알아두기
도커 컴포즈는 컨테이너를 직접 만드는 도구가 아니에요. 이미 만들어진 도커 이미지들을 조합해서 하나의 시스템을 구성하는 ‘조립 설계도’ 역할을 한다고 생각하면 훨씬 이해하기 쉬워요.

도커(Docker)와 도커 컴포즈(Docker Compose) 비교

많은 분이 이 둘의 차이를 궁금해하세요. 표를 통해 한눈에 비교해 드릴게요.

구분 도커(Docker CLI) 도커 컴포즈(Docker Compose)
주요 대상 개별 컨테이너 관리 다중 컨테이너 시스템 관리
실행 방식 명령어마다 옵션 입력(run, build 등) YAML 파일 기반 일괄 실행
네트워크 설정 사용자가 직접 생성 및 연결 필요 자동으로 공통 네트워크 생성
환경 공유 각 명령어마다 변수 지정 필요 파일 내에 통합 관리 가능

따라서 개발 환경을 구축하거나, 마이크로서비스 아키텍처(MSA)를 테스트할 때는 도커 컴포즈가 선택이 아닌 필수라고 할 수 있어요. 이제 기초 체력을 길렀으니, 본격적으로 설계도를 그리는 방법을 배워볼까요?

docker-compose.yml 작성부터 실무 실행까지 단계별 가이드

도커 컴포즈의 심장은 바로 docker-compose.yml 파일이에요. 이 파일은 YAML 형식을 사용하는데, 띄어쓰기 하나에 전체 시스템이 무너질 수 있으니 아주 정교하게 작성해야 합니다. 실무에서 가장 많이 쓰이는 구조를 중심으로 단계별로 살펴볼게요.

STEP 1. 서비스의 뼈대 구성하기

가장 먼저 해야 할 일은 어떤 컨테이너들을 띄울지 결정하는 거예요. YAML 파일의 최상위에는 보통 services:라는 키가 옵니다. 그 아래에 우리가 실행하고 싶은 각각의 서비스들을 나열하면 돼요.

예를 들어, 웹 서버와 데이터베이스가 필요하다면 다음과 같이 시작합니다.

services:
web-server:
image: nginx:latest
database:
image: mysql:8.0

여기서 image는 도커 허브(Docker Hub)에서 가져올 이미지 이름을 말해요. 만약 직접 만든 이미지를 사용하고 싶다면 build: . 옵션을 사용해서 현재 디렉토리의 Dockerfile을 읽어오도록 설정할 수 있어요. 이 단계에서 중요한 건 각 서비스가 독립적인 단위로 존재하면서도 하나의 파일 안에서 관리된다는 점이에요.

STEP 2. 포트와 환경 변수 설정하기

서비스를 정의했다면, 이제 외부와 소통할 통로를 열어줘야 해요. 외부에서 접속할 포트와 컨테이너 내부에서 사용할 설정값들을 지정하는 단계입니다.

ports: 옵션은 ‘호스트 포트:컨테이너 포트’ 형식으로 작성해요. 만약 내 컴퓨터의 8080 포트로 접속했을 때 컨테이너의 80 포트로 연결하고 싶다면 - "8080:80"이라고 적으면 됩니다. 이때 숫자를 따옴표로 감싸주는 것이 오류를 방지하는 좋은 습관이에요.

또한, 데이터베이스 비밀번호 같은 민감한 정보는 environment: 옵션을 통해 전달합니다. 이렇게 하면 이미지 자체를 수정하지 않고도 실행 시점에 원하는 설정을 주입할 수 있어 매우 안전하고 유연해요.

STEP 3. 데이터 보존을 위한 볼륨(Volume) 연결하기

컨테이너는 기본적으로 ‘휘발성’이에요. 컨테이너를 삭제하면 그 안에 저장된 데이터도 모두 사라지죠. 데이터베이스의 데이터가 날아간다면 정말 끔찍한 일이겠죠? 이를 방지하기 위해 볼륨(Volume) 설정이 반드시 필요해요.

볼륨은 호스트 컴퓨터의 특정 폴더와 컨테이너 내부의 폴더를 연결하는 기능이에요. volumes: 옵션을 사용하며, 두 가지 방식이 있어요.

  • Bind Mount: 내 컴퓨터의 특정 경로(예: ./data)를 직접 지정하는 방식이에요. 설정이 직관적이라 개발할 때 많이 써요.
  • Named Volume: 도커가 관리하는 영역에 이름을 붙여 저장하는 방식이에요. 성능이 더 좋고 관리가 편해서 운영 환경에서 추천해요.

STEP 4. 서비스 간의 네트워크와 의존성 정의하기

웹 서버는 데이터베이스에 접속해야 하고, 데이터베이스는 네트워크를 통해 웹 서버의 요청을 받아야 해요. 도커 컴포즈는 기본적으로 모든 서비스가 하나의 가상 네트워크에 포함되도록 설계되어 있어요. 덕분에 컨테이너 이름만으로 서로를 찾을 수 있는 서비스 디스커버리(Service Discovery) 기능이 작동합니다.

예를 들어, 웹 서버 설정에서 DB 주소를 localhost가 아닌 database(서비스 이름)로 적으면 도커 컴포즈가 알아서 연결해 줘요. 여기에 추가로 depends_on: 옵션을 사용하면, “데이터베이스가 먼저 뜬 다음에 웹 서버를 띄워라”와 같은 실행 순서를 제어할 수 있어 매우 편리합니다.

STEP 5. 실무 적용 시나리오: 웹 + DB 통합 환경

지금까지 배운 내용을 종합하여, 실제 작동하는 하나의 완성된 예시를 보여드릴게요. 이 코드를 그대로 복사해서 테스트해 보셔도 좋아요.

version: '3.8'
services:
db-server:
image: postgres:15
environment:
POSTGRES_PASSWORD: mysecretpassword
volumes:
- db_data:/var/lib/postgresql/data
app-server:
build: .
ports:
- "3000:3000"
depends_on:
- db-server
environment:
DATABASE_URL: postgres://db-server:5432/mydb

volumes:
db_data:

이 설정 파일은 db-server라는 이름의 PostgreSQL을 실행하고, app-server라는 이름의 사용자 정의 앱을 띄웁니다. app-serverdb-server가 완전히 준비될 때까지 기다렸다가 실행되며, 데이터는 db_data라는 볼륨에 안전하게 보관됩니다. 이제 터미널에서 docker-compose up -d 한 줄만 치면 이 모든 시스템이 마법처럼 한꺼번에 작동하게 됩니다.

자주 하는 실수와 해결법 및 궁금증 해결하기

도커 컴포즈를 처음 사용하면 반드시 한 번쯤은 벽에 부딪히게 마련이에요. 제가 경험하며 정리한 가장 흔한 실수와 그 해결책을 정리해 드릴게요.

자주 하는 실수와 해결법

  • 실수: YAML 파일의 들여쓰기 오류
    왜 발생하는가: YAML은 띄어쓰기(Space) 개수로 구조를 파악하는데, 탭(Tab)을 섞어 쓰거나 칸 수가 맞지 않으면 문법 오류가 나요.
    ✅ 해결법: 반드시 스페이스바를 사용하고, VS Code 같은 에디터의 YAML 확장 프로그램을 설치해서 시각적으로 확인하세요.
  • 실수: 포트 충돌 발생
    왜 발생하는가: 이미 내 컴퓨터에서 80번 포트를 다른 프로그램이 쓰고 있는데, 도커 컴포즈로 또 80번을 열려고 할 때 발생해요.
    ✅ 해결법: "8081:80"처럼 호스트 쪽 포트 번호를 바꿔서 지정해 주세요.
  • 실수: 컨테이너 실행 순서와 데이터베이스 연결 실패
    왜 발생하는가: depends_on은 컨테이너가 ‘실행’되는 순서만 보장할 뿐, 데이터베이스 내부의 엔진이 완전히 ‘준비’될 때까지 기다려주지는 않아요.
    ✅ 해결법: 애플리케이션 코드 내에 재시도(Retry) 로직을 넣거나, healthcheck 옵션을 사용하여 서비스가 완전히 준비되었는지 확인해야 해요.
  • 실수: 볼륨 데이터가 사라짐
    왜 발생하는가: 볼륨 설정을 하지 않고 컨테이너 내부 폴더에만 데이터를 쌓으면, 컨테이너 삭제 시 데이터도 같이 삭제돼요.
    ✅ 해결법: 반드시 volumes: 설정을 통해 호스트나 이름 있는 볼륨(Named Volume)에 데이터를 연결하세요.
  • 실수: 환경 변수 인식 불가
    왜 발생하는가: .env 파일을 사용하면서 파일 위치가 틀리거나, 변수 이름을 잘못 적는 경우가 많아요.
    ✅ 해결법: docker-compose.yml과 같은 경로에 .env 파일을 두고, 변수명에 오타가 없는지 다시 확인하세요.
⚠️ 주의
실제 운영 환경에서는 비밀번호 같은 민감한 정보를 docker-compose.yml에 직접 적지 마세요. 반드시 별도의 환경 변수 파일이나 비밀 관리 도구를 사용해야 보안 사고를 막을 수 있습니다.

자주 묻는 질문

Q. 도커 컴포즈와 쿠버네티스(Kubernetes) 중 무엇을 써야 하나요?

규모의 차이라고 보시면 돼요. 도커 컴포즈는 단일 서버에서 여러 컨테이너를 관리하기에 최적화된 도구예요. 반면 쿠버네티스는 수십, 수백 대의 서버를 관리하는 거대한 시스템을 위한 도구입니다. 처음 시작하신다면 도커 컴포즈로 충분해요.

Q. 수정된 설정 파일을 적용하려면 어떻게 하나요?

파일을 수정한 뒤 다시 docker-compose up -d를 입력하면 됩니다. 도커 컴포즈는 똑똑해서 변경된 부분만 감지하여 해당 컨테이너만 새로 만들고 다시 실행해 줍니다.

Q. 실행 중인 컨테이너의 로그를 보고 싶어요.

docker-compose logs -f 명령어를 사용하세요. -f 옵션을 붙이면 실시간으로 올라오는 로그를 계속 지켜볼 수 있어서 디버깅할 때 매우 유용합니다.

Q. 컨테이너를 완전히 삭제하고 싶을 때는요?

docker-compose down 명령어를 사용하세요. 이 명령은 실행 중인 컨테이너뿐만 아니라 생성된 네트워크까지 깔끔하게 정리해 줍니다. 만약 볼륨까지 지우고 싶다면 docker-compose down -v를 입력하면 됩니다.

도커 컴포즈 마스터를 위한 마무리 요약

지금까지 도커 컴포즈의 기본 개념부터 실제 파일 작성법, 그리고 실무에서 겪을 수 있는 문제들까지 모두 살펴보았어요. 처음에는 YAML 문법이 낯설고 복잡해 보일 수 있지만, 한 번 구조를 이해하고 나면 이보다 편리한 도구가 없다는 걸 느끼실 거예요.

✅ 핵심 요약

  • 도커 컴포즈는 여러 컨테이너를 하나의 설계도(YAML)로 관리하는 도구예요.
  • services는 역할, ports는 통로, volumes는 저장소를 의미해요.
  • 서비스 간 연결은 컨테이너 이름만으로 가능한 ‘서비스 디스커버리’를 활용하세요.
  • 데이터 유실을 막으려면 반드시 볼륨(Volume) 설정을 해야 해요.
  • 설정 변경 후에는 docker-compose up -d로 즉시 반영할 수 있어요.

이제 이론 공부는 충분합니다. 다음 단계로 넘어가 볼까요? 가장 좋은 학습 방법은 직접 해보는 것이에요.

🚀 지금 바로 실행해 보세요!
위의 본문에 있는 docker-compose.yml 예시 코드를 복사해서 여러분의 테스트 서버나 로컬 컴퓨터에 저장해 보세요. 그리고 docker-compose up -d 명령어를 입력해 보세요. 컨테이너들이 차례대로 뜨는 모습을 보면 훨씬 빠르게 감이 오실 거예요.

설정 과정에서 막히는 부분이 있다면 언제든 공식 문서를 참고하거나 커뮤니티에 질문하는 것을 두려워하지 마세요. 꾸준히 컨테이너를 다루다 보면 어느새 인프라를 자유자재로 다루는 여러분을 발견하게 될 거예요.

관련해서 더 깊이 있는 내용이 궁금하다면 다음 글도 함께 읽어보시길 권장해요.
도커 컴포즈 기본 개념 시작하기 — 설치부터 첫 실행까지 30분 따라하기

댓글 남기기