들어가며
안녕하세요 Noah입니다.
오늘은 기존 가상 머신(VM) 방식과 대비되는 Docker 컨테이너의 핵심 가상화 원리를 살펴보고, 로컬 개발 환경을 한층 더 쾌적하게 만들어주는 Docker Compose의 watch 기능에 대해 정리해 보겠습니다.
1. 컨테이너 가상화와 기존 VM의 차이
Docker는 컨테이너(Container)라는 가상화 기술을 통해 애플리케이션과 그 실행 환경을 패키징하고 실행하는 플랫폼입니다. 기존의 가상 머신(Virtual Machine, VM) 방식과 비교할 때 구조적으로 훨씬 가볍고 빠르다는 특징이 있습니다.
기존 VM 환경은 하이퍼바이저(Hypervisor)를 거쳐 각 가상 머신마다 독립된 무거운 Guest OS를 부팅해야 했습니다. 반면, 컨테이너 기술 환경은 호스트 운영체제의 커널을 공유하면서 필요한 프로세스와 실행 환경만을 격리하여 실행합니다.
flowchart TD
subgraph VM ["가상 머신 (Virtual Machine)"]
direction BT
V_HW["Infrastructure"] --> V_Host["Host OS"]
V_Host --> V_Hyper["Hypervisor"]
V_Hyper --> V_Guest1["Guest OS"] --> V_App1["App A"]
V_Hyper --> V_Guest2["Guest OS"] --> V_App2["App B"]
end
subgraph Container ["컨테이너 (Docker)"]
direction BT
C_HW["Infrastructure"] --> C_Host["Host OS"]
C_Host --> C_Engine["Docker Engine"]
C_Engine --> C_App1["App A"]
C_Engine --> C_App2["App B"]
end
[!TIP]
컨테이너는 자체적인 OS 전체를 띄우지 않기 때문에 부팅 시간이 사실상 프로세스 시작 시간과 동일할 정도로 짧습니다. 이로 인해 리소스를 극적으로 절약하고 빠른 실행 속도를 보장할 수 있습니다.
2. Docker Hub의 역할
Docker Hub는 전 세계의 개발자들이 컨테이너 이미지를 검색하고, 다운로드하며, 공유할 수 있는 중앙 이미지 저장소(Registry) 역할을 합니다.
검증된 공식 이미지(Official Image)부터 오픈소스 커뮤니티가 만든 다양한 환경까지 준비되어 있으며, 복잡한 설치 과정 없이 아래 명령어 하나로 간편하게 환경을 가져올 수 있습니다.
# Docker Hub에서 Nginx 공식 이미지 다운로드
docker pull nginx:latest

3. Docker Compose 구성과 Watch 설정
하나의 서비스는 보통 웹 서버, API 서버, 데이터베이스 등 여러 개의 컨테이너 조합으로 이루어집니다. 이를 하나의 명세서로 쉽게 관리하기 위해 Docker Compose를 사용합니다.
아래는 로컬 개발 시 매우 유용하게 사용할 수 있는 develop.watch 기능이 포함된 docker-compose.yml 예시입니다.
services:
web:
build: .
command: npm start
develop: # 로컬 개발 환경을 위한 설정
watch:
- action: sync
path: ./web
target: /app/web
ignore:
- node_modules/
- action: sync+restart
path: ./proxy/nginx.conf
target: /etc/nginx/conf.d/default.conf
backend:
build:
context: backend
target: builder # 멀티 스테이지 빌드 타겟 지정
[!NOTE]
sync와 sync+restart 옵션은 언제 사용할까?
이 옵션들은 일반 배포용 Compose 문법이 아닌, Docker Compose 최신 버전에서 지원하는 로컬 개발용 기능(Watch)입니다.
sync: 로컬 호스트(path)에서 파일이 변경되면 컨테이너 재시작 없이 내부 경로(target)로 즉시 동기화합니다. React나 Node.js처럼 핫 리로딩(Hot Reloading)이 지원되는 환경에서 코드를 수정할 때 사용합니다.sync+restart: 파일 동기화 후 컨테이너를 강제로 재시작합니다. Nginx 설정 파일(nginx.conf)처럼 변경 사항을 적용하기 위해 서비스 자체를 재기동해야 하는 경우에 사용합니다.
[!TIP]
build.target은 어떤 상황에서 구분할까?backend서비스에 작성된target: builder는Dockerfile내에 멀티 스테이지 빌드(Multi-stage build)가 구성되어 있을 때 사용합니다.
운영 배포 시에는 소스 코드가 제거된 가벼운 최종 단계 이미지를 쓰지만, 로컬 개발 시에는 테스트 도구나 소스 코드가 포함된builder단계의 이미지를 타겟으로 삼아 디버깅을 원활하게 하기 위한 목적입니다.
[!OUTRO]
컨테이너는 표면적으로 가볍고 편리해 보이지만, 그 동작 원리를 제대로 이해하지 못하면 실무에서 무겁고 복잡한 트러블슈팅을 겪게 됩니다. 가벼운 구조 뒤에 숨겨진 강력한 철학을 이해한다면, 컨테이너는 단순한 실행 도구가 아니라 더 견고한 아키텍처를 설계하는 방식이 되어줄 것입니다.
'개발 노트' 카테고리의 다른 글
| JPA 동작 원리와 영속성 컨텍스트 완벽 이해하기 (0) | 2026.02.10 |
|---|---|
| MySQL 데이터베이스 이름 변경 불가 문제와 RENAME TABLE로 안전하게 마이그레이션하는 방법 (0) | 2026.02.10 |
| Docker로 로컬 환경에 MySQL 설치하고 접속하는 방법 (0) | 2026.02.10 |