콘텐츠로 바로가기

Containerization & Docker Mechanics

애플리케이션과 그 실행 환경을 표준화된 단위로 묶는 가상화 기술과, 운영체제 수준에서 격리된 공간을 만드는 컨테이너 물리학을 다루는 학습 노드입니다.

지식 성숙도: evergreen

목차 보기22

1. Overview

컨테이너화와 도커 역학(Containerization & Docker Mechanics)은 "내 노트북에서는 잘 되는데요?"라는 개발자의 변명을 영원히 박살 내고, OS부터 애플리케이션 코드까지 통째로 얼려서(Image) 지구상 어디든 똑같이 복제해 내는 현대 인프라의 표준 배송 규격을 해부합니다.

학습자는 무거운 하드웨어를 통째로 가상화하던 **가상 머신(Virtual Machine, Hypervisor)**의 비효율을 깨닫고, 리눅스 커널(Kernel)을 공유하면서 프로세스만 감옥(Namespace)에 가두는 **컨테이너(Container)**의 극단적인 가벼움을 뜯어봅니다. 나아가 Dockerfile을 통해 인프라 구축을 한 줄 한 줄의 코드(IaC)로 선언하고, 수천 개의 이미지를 효율적으로 겹쳐(Layer) 빌드 속도를 기하급수적으로 끌어올리는 **도커 이미지 레이어 아키텍처(Union File System)**를 장악합니다. 마지막으로, 컨테이너가 파괴되면 내부 데이터도 영원히 날아가는 휘발성(Ephemeral)의 한계를 깨고 볼륨(Volume) 마운트를 통해 생명력을 연장하는 인프라 튜닝 역량을 확보합니다.

2. Scope & Boundaries

In-Scope

  • Virtual Machine vs Container: Hypervisor(OS 가상화)와 Linux Container(프로세스 격리)의 물리적 차이.
  • Linux Kernel Features: Namespaces(자원 격리), cgroups(자원 할당 제한).
  • Docker Architecture: Docker Daemon, Client, Registry, Image, Container.
  • Image Layering (UnionFS): 캐싱을 활용한 Dockerfile 최적화, Multi-stage Build (이미지 다이어트).

Out-of-Scope

  • Kubernetes 기반 100개 컨테이너 자동 관리: → 07-06-03 Kubernetes & Cluster Orchestration 영역으로 위임 (본 문서는 단일 컨테이너 혹은 Docker-Compose 수준에 집중).
  • CI/CD 파이프라인 자동 배포: → 09-02 CI/CD & DevOps 영역.

Boundaries

  • Container는 미니 리눅스가 아니다: 초보자들은 도커 컨테이너 안에 SSH로 접속해서 apt-get install을 치고 설정을 바꿉니다. 이는 가상 머신(VM) 시절의 낡은 사고방식입니다. 컨테이너는 불변(Immutable)해야 하며 언제든 죽이고 새로 띄울 수 있는 '일회용 소모품(Disposable)'입니다. 변경 사항이 있다면 컨테이너 안에서 수정할 것이 아니라, Dockerfile을 고쳐서 완전히 새로운 이미지를 빌드해야 한다는(Immutable Infrastructure) 선을 명확히 긋습니다.

3. Counterexample

  • 10GB짜리 괴물 이미지: Dockerfile을 대충 짰습니다. 우분투 풀 버전을 베이스로 깔고, 빌드 도구(gcc)와 수많은 패키지를 설치한 뒤 소스코드를 컴파일했습니다. 최종 도커 이미지가 5GB가 되었습니다. 배포할 때마다 서버가 5GB를 다운로드하느라 배포 시간이 30분씩 걸립니다. 컴파일에 쓴 도구(gcc)는 버리고 최종 실행 파일(Binary)만 쏙 빼서 50MB짜리 알파인(Alpine) 이미지로 만드는 Multi-stage Build 기술을 모르는 자원의 학살입니다.
  • 데이터 휘발의 공포 (Ephemeral Death): 도커 컨테이너 안에 MySQL을 띄웠습니다. 유저 데이터가 착실히 쌓이고 있습니다. 어느 날 docker stop 후 docker rm으로 컨테이너를 지우고 새 버전으로 업데이트했습니다. 유저 데이터가 흔적도 없이 증발했습니다. 컨테이너의 파일 시스템은 컨테이너와 운명을 함께한다는 불변의 법칙을 무시하고, 호스트 OS의 디스크를 연결하는 볼륨(Volume) 마운트를 빼먹은 초보적인 대참사입니다.

4. Prerequisites

  • 리눅스 OS 기초 (Basic): 프로세스와 파일 시스템 계층 구조. (03-01 OS Core)
  • 가상화 개념 (Basic): 하드웨어 가상화와 OS. (03-02 Networking Basics)

5. Learning Map

Sequence Core Cluster Objective & Description Evidence (BoK)
1 VM vs Container 무거운 OS 전체를 띄우는 VM의 사슬을 끊고, 커널은 빌려 쓰면서 프로세스만 눈속임(격리)하는 컨테이너의 가벼움을 쥡니다. P1:CS2023
2 The Magic of Namespaces 1번 프로세스(init)조차 격리시켜, 컨테이너 안에서는 자기가 서버의 유일한 주인인 줄 착각하게 만드는 리눅스 커널의 환술을 해부합니다. P5:SFIA
3 Dockerfile & UnionFS RUN, COPY 한 줄마다 얇은 비닐(Layer)이 생성되고 겹쳐져, 빌드 속도와 용량을 미친 듯이 최적화하는 이미지 아키텍처를 뜯어봅니다. Industry:Architecture
4 Immutability & Multi-stage 한 번 만든 이미지는 절대 변하지 않는다는 불변성 철학과, 쓰레기를 버리고 알맹이만 빼내는 다단계 빌드(Multi-stage)의 미학을 장악합니다. Industry:Backend

6. Learning Topics

Basic

Core Topic 01: 무거운 OS를 벗어던지다 (VM vs Container)

  • Why to Learn: 애플리케이션 하나 띄우겠다고 2GB짜리 OS 10개를 부팅하던 구시대 가상 머신(VM)의 비효율을 깨고, 단 1초 만에 켜지는 컨테이너의 구조적 승리를 이해하기 위함입니다.
  • What to Learn:
    • Concepts: Hypervisor, Guest OS, Container Engine (Docker), Host OS Kernel Sharing, Ephemeral (휘발성).
    • Skills: VM과 Container의 아키텍처 다이어그램 비교 및 부팅 속도(Overhead)의 물리적 차이 도출.
  • How to Learn:
    • 1단계: VM의 딜레마: 집(물리 서버) 안에 방 3개를 만듭니다. VM은 각 방마다 화장실, 주방, 보일러(OS)를 전부 따로 설치합니다. 무겁고 비쌉니다.
    • 2단계: 컨테이너의 공용화: 컨테이너는 주방과 보일러(리눅스 커널)를 하나만 두고, 각 방에는 칸막이(격리)만 칩니다. 애플리케이션 입장에서는 자기 방만 보이니까 독립적이라고 느끼지만, 실제 하드웨어 제어는 공용 커널이 다 해주는 극강의 효율을 해부합니다.
  • Implement: 도커 컨테이너 부팅 속도 시뮬레이션. 터미널에서 time docker run ubuntu echo "Hello"를 실행하면 1초도 안 걸려서 끝남. OS 부팅 과정(Init, Systemd)이 아예 생략되고 오직 echo 프로세스 하나만 실행됨을 터미널 로그로 증명.

Core Topic 02: 리눅스 커널의 환술, 격리와 통제 (Namespaces & cgroups)

  • Why to Learn: "도커는 어떻게 프로세스들을 완벽히 분리하는가?"에 대한 답이 결국 도커의 마법이 아니라 리눅스 커널의 기본 기능(Namespace, cgroup)을 포장한 것임을 꿰뚫기 위함입니다.
  • What to Learn:
    • Concepts: Linux Namespace (PID, NET, MNT - 논리적 격리), Control Groups (cgroups - 물리적 자원 제한).
    • Skills: 특정 컨테이너가 호스트 CPU를 100%100\% 잡아먹는 현상을 막기 위한 리소스 쿼터(Quota) 할당.
  • How to Learn:
    • 1단계: Namespace (보이지 않는 벽): 호스트 서버에는 1,000개의 프로세스가 돌고 있습니다. 도커가 컨테이너를 띄우면, 그 컨테이너 안의 프로세스에게 PID Namespace라는 안경을 씌웁니다. 이 프로세스는 자기가 "PID 1번(대장)"인 줄 알고, 다른 999개의 프로세스를 아예 보지(View) 못하는 착각의 감옥을 해부합니다.
    • 2단계: cgroups (물리적 목줄): A 컨테이너가 버그에 걸려 메모리를 무한대로 씁니다. 호스트 OS가 뻗기 전에 리눅스 cgroup이 작동하여 "너는 RAM 500MB까지만 써!"라며 가차 없이 OOM(Out of Memory)으로 컨테이너를 죽여버리는 자원 통제 기전을 뜯어봅니다.
  • Implement: CPU 강제 제한 데모. docker run --cpus=".5" ubuntu stress --cpu 1 실행. 호스트 OS에서 htop으로 확인하면, 컨테이너 안의 stress 프로세스가 아무리 CPU를 100%100\% 쓰려고 발악해도, 실제 호스트 CPU 코어 하나 기준으로는 정확히 50%50\% 만 점유하는 cgroup의 통제력 렌더링.

Practical

Core Topic 03: 비닐을 겹쳐라, 도커 이미지 레이어 (Dockerfile & UnionFS)

  • Why to Learn: 무지성으로 Dockerfile을 짜면 코드를 한 줄만 고쳐도 전체 이미지를 다시 다운받아야 하는(캐시 무효화) 재앙을 막고, 캐시(Cache)를 극대화하는 빌드 최적화 역량을 장악하기 위함입니다.
  • What to Learn:
    • Concepts: Dockerfile 명령어 (FROM, RUN, COPY, CMD), Union File System (UnionFS), Image Layers, Layer Caching (레이어 캐싱).
    • Skills: 변경이 잦은 코드(Source)와 변경이 드문 의존성(npm install)의 순서를 배치하는 Dockerfile 캐싱 최적화 설계.
  • How to Learn:
    • 1단계: UnionFS (셀로판지 겹치기): 도커 이미지는 하나의 큰 파일이 아닙니다. FROM ubuntu (1번 비닐), RUN apt-get (2번 비닐), COPY . . (3번 비닐)처럼 투명한 셀로판지를 겹겹이 쌓아 올린 구조(Layer)입니다. 아래쪽 비닐은 누구나 공유해서 쓸 수 있어 디스크 용량을 획기적으로 아끼는 구조를 해부합니다.
    • 2단계: 캐싱의 저주: COPY . . (소스 코드 복사)를 먼저 하고 RUN npm install (라이브러리 설치)을 하면, 코드를 한 글자만 고쳐도 캐시가 깨져서 무거운 라이브러리를 매번 새로 설치해야 합니다. "자주 변하지 않는 것을 무조건 위에 둔다"는 Dockerfile 작성의 절대 법칙을 뜯어봅니다.
  • Implement: 안 좋은 Dockerfile vs 훌륭한 Dockerfile 빌드 속도 비교.
    • Bad: COPY . . → RUN pip install -r req.txt
    • Good: COPY req.txt . → RUN pip install -r req.txt → COPY . . 소스 코드를 살짝 고친 뒤 두 번째 빌드(Re-build)를 돌렸을 때, Good 버전이 [CACHED]를 띄우며 1초 만에 빌드되는 기적을 터미널 로그로 증명.

Advanced

Core Topic 04: 불변의 인프라와 껍데기 벗기기 (Multi-stage & Volumes)

  • Why to Learn: 불변성(Immutable)을 지키기 위해 컨테이너 내부 데이터를 포기할 것인지, 영속성(Volume)을 위해 구멍을 뚫어줄 것인지 통제하고, 프로덕션 배포 이미지의 용량을 극한으로 깎아내리기 위함입니다.
  • What to Learn:
    • Concepts: Multi-stage Build (다단계 빌드), Docker Volumes (Bind mount, Named volume), Immutable Infrastructure (불변 인프라).
    • Skills: 빌드 도구와 런타임 환경을 분리하여 초경량(Alpine) 프로덕션 이미지를 추출하는 Multi-stage 작성.
  • How to Learn:
    • 1단계: Multi-stage Build (쓰레기 버리기): Go 언어로 코드를 짭니다. 빌드하려면 1GB짜리 golang 이미지가 필요합니다. 하지만 빌드가 끝나면 남는 main 실행 파일은 단 10MB입니다. 1단계(Builder)에서 1GB 이미지로 컴파일만 싹 하고, 2단계에서 깨끗한 5MB짜리 alpine 이미지에 실행 파일 10MB만 쓱 넘겨 담아 총 15MB짜리 프로덕션 이미지를 뽑아내는 다이어트 기법을 해부합니다.
    • 2단계: Volume (영속성의 구멍): 컨테이너는 불변해야 하므로 내부에서 쌓이는 DB 데이터는 컨테이너가 죽으면 날아갑니다. 이를 막기 위해 컨테이너의 /var/lib/mysql 디렉토리에 호스트 OS의 디스크를 연결(Mount)하여, 컨테이너를 지워도 데이터는 호스트에 안전하게 살아남는 볼륨의 역학을 뜯어봅니다.
  • Implement: Multi-stage Dockerfile 작성 및 Size 비교. AS builder 구문을 사용하여 자바 소스 코드를 maven 이미지에서 mvn package 로 컴파일하고, 아래에서 FROM openjdk:jre를 새로 열어 .jar 파일만 복사(COPY --from=builder)해 오는 데모. 기존 500MB 이미지와 최적화된 100MB 이미지의 크기(docker images) 콘솔 출력 비교.

7. Terminology

Term (EN / ko, abbr) 1문장 정의 단계(기본/권장/실무/심화) 역할/맥락 관련 개념 유사/대비/함께 사용 오해 포인트 Evidence(Primary/Secondary/Industry:ID) Flags(core)
Containerization (컨테이너화) 애플리케이션이 돌아가는 데 필요한 코드, 런타임, 시스템 도구, 라이브러리를 하나의 상자(Image)로 묶어, 윈도우든 맥이든 리눅스 호스트든 어디서나 똑같이 실행되게 만드는 인프라 혁명입니다. 기본 애플리케이션 격리 및 배송 Docker Image / Dockerfile Virtual Machine (VM) 컨테이너는 그 자체로 완전한 OS가 아니며, 호스트 리눅스의 커널(심장)을 빌려 쓰는 껍데기에 불과함 P1:CS2023:SE core
Linux Namespace 리눅스 커널이 제공하는 기능으로, 프로세스마다 각자의 고유한 PID(프로세스 ID), 네트워크 IP, 마운트 지점을 부여하여 자기가 서버의 유일한 주인인 것처럼 눈속임하는 논리적 격리벽입니다. 권장 프로세스 격리 원리 cgroups / Docker Engine Chroot 도커가 만든 기술이 아니라, 원래 리눅스에 있던 기능을 도커가 예쁘게 포장해서 쓰기 쉽게 만든 것임 P5:SFIA:ITOP core
Union File System (UnionFS) Dockerfile의 명령어 한 줄 한 줄을 독립적인 읽기 전용 레이어(Layer)로 만들고, 이를 차곡차곡 투명하게 겹쳐서 하나의 완성된 파일 시스템으로 보여주는 도커 이미지의 핵심 아키텍처입니다. 실무 이미지 레이어 캐싱 Image Caching Copy-on-Write (CoW) 하위 레이어의 파일을 상위 레이어에서 수정하면, 덮어쓰는(Copy-on-Write) 방식이므로 이미지 용량은 오히려 늘어남 Industry:Architecture core
Multi-stage Build 컨테이너 이미지가 뚱뚱해지는 것을 막기 위해, 1단계 컨테이너에서 코드를 컴파일(빌드)하고, 2단계 텅 빈 경량 컨테이너로 '완성된 실행 파일'만 쏙 옮겨 담는 궁극의 다이어트 기법입니다. 심화 프로덕션 이미지 최적화 Alpine Linux / Dockerfile Builder Pattern 소스 코드 유출 방지와 공격 표면(Attack Surface) 최소화를 위해 보안 측면에서도 반드시 적용해야 함 Industry:Backend core

8. References

Primary

  • [P1] CS2023 - Software Engineering (SE) - Software Architecture and Containerization
  • [P5] SFIA - IT Infrastructure (ITOP) - Systems Installation and Removal

Secondary

  • [Docker Deep Dive] Nigel Poulton - Containers vs VMs, Images, and Architecture
  • [The Docker Book] James Turnbull - Building and Managing Images

Industry

  • [Docker Official Documentation] - Best practices for writing Dockerfiles
  • [Red Hat] - What is a Linux container? (Namespaces and cgroups)

9. Final Checklist

Primary

  • 하드웨어 하이퍼바이저 위에서 무거운 Guest OS를 여러 개 부팅하는 가상 머신(VM)과, 호스트 OS 커널 하나를 공유하며 프로세스만 격리하는 컨테이너(Container)의 성능 및 오버헤드 차이를 설명할 수 있는가?
  • 도커 컨테이너 안에서 돌아가는 프로세스들이 어떻게 호스트 서버의 다른 프로세스나 파일 시스템에 접근하지 못하는지, 리눅스 네임스페이스(Namespaces)의 역할을 증명할 수 있는가?

Secondary

  • 컨테이너가 무한 루프에 빠져 메모리 누수가 발생했을 때, 호스트 OS 전체가 뻗지 않고 해당 컨테이너만 메모리 초과(OOM)로 깔끔하게 죽여버리는 리눅스 컨트롤 그룹(cgroups)의 통제 역학을 해부할 수 있는가?
  • Dockerfile을 작성할 때, 소스 코드 복사(COPY . .) 명령어와 라이브러리 설치(RUN npm install) 명령어의 순서가 도커 이미지 레이어 캐싱(Layer Caching)과 빌드 속도에 미치는 치명적 영향을 논증할 수 있는가?

Industry

  • 프로덕션에 배포할 도커 이미지 용량을 1GB에서 50MB로 줄이고 보안 취약점(Attack Surface)을 최소화하기 위해, 멀티 스테이지 빌드(Multi-stage Build) 패턴과 경량화된 Alpine 이미지를 결합할 수 있는가?
  • 도커 컨테이너는 불변(Immutable)하고 언제든 삭제될 수 있는 휘발성(Ephemeral)을 가짐을 인지하고, 데이터베이스 컨테이너의 유저 데이터를 보호하기 위해 호스트 디스크를 마운트하는 도커 볼륨(Docker Volume) 아키텍처를 설계할 수 있는가?

System Architecture · Microservices & Containers

2 / 6