Docker 배포 초보 가이드 2026 — 컨테이너로 앱 올리기 첫걸음
이 페이지의 일부 링크는 제휴 링크이며, 구매 시 추가 비용 없이 소정의 수수료를 받을 수 있습니다.
"내 컴퓨터에서는 되는데 서버에서는 안 돼요." 개발하면서 한 번쯤 들어본 말일 겁니다. Node 버전이 다르거나 라이브러리가 로컬에만 깔려 있어 생기는 문제죠. Docker는 애플리케이션과 실행 환경을 통째로 포장해서 옮기는 방식으로 이 문제를 풉니다. 이 글은 Docker를 처음 접하는 개발자를 대상으로 핵심 개념부터 아주 간단한 배포 흐름까지 첫걸음을 따라갑니다.
짧은 결론
- Docker는 애플리케이션과 실행 환경(라이브러리, 설정)을 통째로 묶어 어디서든 똑같이 돌아가게 해줍니다.
- 핵심 개념은 이미지(설계도), 컨테이너(실행 중인 인스턴스), Dockerfile(이미지를 만드는 레시피) 세 가지입니다.
- 흐름은 단순합니다: Dockerfile 작성 →
docker build로 이미지 생성 →docker run으로 컨테이너 실행. - 서버 배포는 로컬에서 만든 이미지를 레지스트리에 올리고, 서버에서 내려받아 실행하는 방식이 기본 골격입니다.
- 초보 단계에서는 포트 매핑, 이미지 용량, 데이터 보존(볼륨)에서 자주 막힙니다.
Docker/컨테이너가 왜 편한가 — 환경 일치
전통적인 배포는 서버에 언어 런타임, 라이브러리, 설정 파일을 하나하나 맞춰가며 설치합니다. 이 과정에서 로컬 환경과 서버 환경이 미묘하게 어긋나면 "로컬에서는 되는데 서버에서는 안 되는" 문제가 생깁니다.
Docker는 코드뿐 아니라 그 코드가 필요로 하는 런타임 버전, 라이브러리, 환경 변수까지 하나의 이미지로 묶습니다. 이 이미지를 실행하면 노트북이든 클라우드 서버든 동일한 환경이 만들어집니다. 가상머신(VM)이 OS 전체를 복제해 무거운 것과 달리, 컨테이너는 호스트 OS 커널을 공유하며 필요한 부분만 격리해 가볍고 시작도 빠릅니다.
핵심 개념 세 가지
| 용어 | 의미 | 비유 |
|---|---|---|
| 이미지(Image) | 실행에 필요한 모든 것을 담은 읽기 전용 템플릿 | 요리 레시피 |
| 컨테이너(Container) | 이미지를 실제로 실행한 결과물 | 레시피로 만든 요리 |
| Dockerfile | 이미지를 어떻게 만들지 정의하는 텍스트 파일 | 레시피를 적는 종이 |
Dockerfile을 작성하면 이미지가 만들어지고, 그 이미지를 실행하면 컨테이너가 됩니다. 같은 이미지로 컨테이너를 여러 개 띄울 수 있고, 컨테이너를 지웠다가 다시 만들어도 이미지만 있으면 동일한 상태를 재현할 수 있습니다.
아주 간단한 예시 흐름
간단한 Node.js 앱 기준으로 프로젝트 루트에 Dockerfile을 만듭니다.
FROM node:20-alpine
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
EXPOSE 3000
CMD ["node", "server.js"]
FROM은 기본 이미지, WORKDIR은 작업 디렉터리, COPY·RUN은 파일 복사와 의존성 설치, CMD는 컨테이너 시작 시 실행할 명령입니다. 이제 이미지를 빌드하고 실행합니다.
docker build -t my-app .
docker run -p 3000:3000 my-app
docker build는 이미지를 만들고(-t로 이름 지정), docker run은 그 이미지로 컨테이너를 띄웁니다. -p 3000:3000은 컨테이너 안 3000번 포트를 내 컴퓨터 3000번 포트에 연결한다는 뜻으로, 이 매핑이 없으면 컨테이너가 떠 있어도 브라우저에서 접속할 수 없습니다.
실제 서버에 올리는 큰 그림
로컬에서 컨테이너가 잘 돌아가는 걸 확인했다면 다음은 서버 배포입니다.
- 로컬(또는 CI)에서 이미지를 빌드합니다.
- 이미지를 Docker Hub 같은 레지스트리에 푸시합니다.
- 서버에서 이미지를 내려받습니다(
docker pull). - 서버에서
docker run으로 컨테이너를 실행합니다.
만든 컨테이너를 어디 서버에 올릴지 고민이라면, 처음에는 관리 부담이 적은 VPS로 시작하는 게 진입 장벽이 낮습니다. DigitalOcean의 Droplet은 Docker가 미리 설치된 이미지를 제공해서, 서버를 만들자마자 docker run 명령만으로 컨테이너를 바로 띄울 수 있습니다. 컨테이너가 여러 개로 늘어나면 이후 Docker Compose나 관리형 서비스로 단계를 올려가면 됩니다.
초보가 자주 막히는 부분
- 포트 매핑 누락:
-p옵션을 빼먹으면 컨테이너는 실행 중인데 외부에서 접속이 안 됩니다.docker ps로 포트 매핑을 항상 확인하세요. - 이미지 용량 과다: 불필요한 파일까지 복사하면 이미지가 커집니다.
.dockerignore로node_modules,.git을 제외하고 가벼운 alpine 계열 베이스 이미지를 쓰면 줄어듭니다. - 데이터 소실: 컨테이너를 삭제하면 그 안에 저장한 데이터도 함께 사라집니다. 유지해야 할 데이터는 볼륨(volume)으로 컨테이너 밖에 저장해야 합니다.
- 이미지·컨테이너 혼동: 컨테이너 안에서 파일을 직접 고쳐도 컨테이너를 지우면 원래 이미지 상태로 돌아갑니다. 변경 사항은 Dockerfile을 고쳐 다시 빌드해야 반영됩니다.
마무리
Docker는 "환경을 코드로 정의해 어디서든 재현한다"는 아이디어에서 출발합니다. 처음에는 이미지·컨테이너·Dockerfile 세 개념을 잡고 로컬에서 빌드·실행을 반복해보는 것으로 충분합니다. 이후 서버에 올리는 경험까지 해보면 왜 많은 팀이 배포 파이프라인에 Docker를 기본으로 두는지 체감하게 될 겁니다.
자주 묻는 질문
Docker와 가상머신(VM)은 뭐가 다른가요?
VM은 OS 전체를 통째로 가상화해 무겁고 느립니다. 컨테이너는 호스트 OS 커널을 공유하며 프로세스 단위로 격리해 훨씬 가볍고 빠르게 시작됩니다. 다만 격리 수준은 VM이 더 높습니다.
이미지를 매번 새로 만들어야 하나요?
코드나 의존성이 바뀌지 않았다면 필요 없습니다. 코드를 수정했다면 다시 빌드하고 기존 컨테이너를 내린 뒤 새 이미지로 재실행하면 됩니다. Docker는 레이어 캐시를 활용해 변경되지 않은 부분은 재사용합니다.
Docker Compose는 꼭 배워야 하나요?
컨테이너 하나만 다룬다면 당장은 필요 없습니다. 다만 웹 서버·데이터베이스처럼 여러 컨테이너를 함께 띄워야 한다면 Compose로 한 번에 정의·실행하는 게 훨씬 편해집니다. 이 글의 흐름에 익숙해진 다음 배우는 걸 추천합니다.