도커 기초부터 컨테이너 오케스트레이션까지: 원티드 백엔드 챌린지 정리
원티드 프리온보딩 백엔드 챌린지 도커편을 정리한 내용입니다.
Docker란 무엇일까?
면접에서 간혹 도커를 써보았느냐? 라는 질문을 받곤 합니다.
도커를 사용하지 않아도 서비스를 개발하고 운영하는데 문제가 없지만, 도커를 사용함으로써 얻을 수 있는 여러 장점들이 있기 때문에 이제는 선택이 아닌 필수가 되고 있습니다. 이런 도커에 대한 개념을 원티드 백엔드 챌린지 도커편 강의를 정리하며 뽀개 보겠습니다.
도커
오픈소스 기반 컨테이너 기반 가상화 도구
또는 애플리케이션을 컨테이너
라는 단위로 격리하여 실행하고 배포할 수 있는 기술입니다.
그럼 컨테이너는 무엇일까요?
컨테이너
컨테이너는 가상화 기술 중 하나입니다.컨테이너를 통해 호스트 운영체제 위에 여러 개의 격리된 환경을 생성을 할 수 있게 됩니다. 또한, 컨테이너 끼리는 격리 되어 있기 때문에 각 컨테이너 안에서 애플리케이션 실행이 가능해집니다.
그럼 가상화 기술은 무엇일까요?
가상화 기술
하나의 물리적인 컴퓨팅 자원(CPU, 메모리, 저장장치)을 가상적으로 분할하여 마치 여러개의 가상 컴퓨터를 사용하는 환경
을 만들어 내는 기술입니다.
이렇게 분할하는 이유는 컴퓨팅 자원을 효율적
으로 사용하고, 서버나 애플리케이션 등을 운영할 때 유연
하며 안정성
을 제공할 수 있기 때문입니다.
가상화 기술 중 하나로 하이퍼 바이저가 있습니다. 이를 컨테이너와 비교하여 컨테이너 가상화 기술이 어떤 점이 뛰어난 지 살펴보겠습니다.
가상 머신 VS 컨테이너
하이퍼바이저
는 가상 머신(가상 환경)을 실행하는 소프트웨어 입니다. 각 가상 머신은 독립적인 운영체제와 커널을 가지기 때문에 머신 간 격리 수준이 높습니다. 즉, 더 높은 보안 수준
을 가질 수 있습니다. 하지만 많은 리소스
가 필요합니다.
컨테이너
는 호스트 운영체제는 공유하고 OS가 아닌 프로세스
를 격리합니다. 각 컨테이너는 OS가 아닌 파일시스템과 라이브러리 등 가상 머신보다 상대적으로 적인 리소스가 필요하기 때문에 더 가볍고 빠릅니다
. 가상 머신 보다 상대적으로 낮은 격리를 제공하지만, 다른 보안기술로 격리를 강화할 수 있습니다.
또한, 컨테이너 단위로 격리/실행/배포하기 때문에 다양한 운영체제에서 사용할 수 있고 컨테이너화된 애플리케이션을 쉽게 빌드/배포/관리 할 수 있습니다.
도커 아키텍쳐
도커 클라이언트
도커 클라이언트는 도커 명령어를 도커 데몬으로 전달하여 상호 작용을 합니다.
도커 데몬
도커 호스트에서 실행되는 도커 데몬 역할은 크게 2가지 입니다.
- 컨테이너 이미지를 관리하고 외부에서 이미지를 다운로드/빌드 작업을 수행합니다.
- 도커 호스트에서 컨테이너를 관리(생성/시작/중지/삭제 등)합니다.
도커 이미지
도커 컨테이너를 만들기 위한 읽기 전용 템플릿 입니다.
도커 컨테이너
애플리케이션을 실행하기 위한 모든 파일과 설정 정보를 포함하는 패키지입니다.
도커 레지스트리
도커 이미지를 관리하고 저장하는 곳입니다. 공개형 저장장소로 도커허브가 있습니다. 도커 레지스트리에서 docker pull로 도커 이미지를 가져오고 docker run명령어를 통해 컨테이너를 실행시킵니다.
도커 네트워크
컨테이너 안 웹 서버는 호스트와 독립적인 환경이기 때문에
별도의 포트번호와 파일시스템
을 갖습니다.
따라서 호스트에서 컨테이너로 포트포워딩
을 해줘야합니다.
또한, 컨테이너가 종료되면 컨테이너 내부에 파일시스템에 접근이 불가하기 때문에 컨테이너의 볼륨을 호스트 디스크에 마운트
해주어야 합니다. 볼륨 마운트를 통해 필요 데이터의 영속성을 보전하고, 컨테이너 간 데이터 교환이나 컨테이너와 호스트 파일 사이에 데이터를 교환 할 수 있습니다.
1
docker network ls
위 명령으로 도커 ID와 DRIVER
종류를 확인할 수 있습니다.
- bridge : 기본 네트워크 드라이버이며 동일한 도커 호스트에서 컨테이너 간의 통신을 도와줍니다.
- host : 호스트의 네트워크를 직접 사용합니다.
- overlay : 서로 다른 도커 호스트의 컨테이너 간 통신을 도와줍니다.
컨테이너 라이프 싸이클
도커 파일
도커 컨테이너 이미지를 생성하는 데 사용되는 텍스트 기반 설정 파일입니다.
도커 파일 내에 컨테이너 안에 들어갈 애플리케이션 및 환경 설정, 종속성, 실행 명령 등을 작성할 수 있습니다. 이 파일을 기반으로 도커 엔진이 자동으로 이미지를 빌드하고 생성할 수 있습니다.
1
2
3
4
5
FROM: 베이스 이미지 선정
WORKDIR: work directory 선정
COPY: 복사할 파일 선정 (예: 작업한 서비스 파일들)
RUN: 실행할 명령어
ENTRYPOINT: 컨테이너가 시작할 때 실행할 명령어 (예: 서버 실행)
Docker Compose란 무엇일까?
여러개의 도커 컨테이너를 실행하기 위해서는 어떻게 해야 할까요? 첫 번째로 도커 네트워크를 생성하고, db, web 등 각 컨테이너를 따로 따로 실행해주어야 합니다.
이런 과정을 일괄적으로 정의하고 제어하기 위해 도커 컴포즈를 사용합니다.
여기서 도커 컴포즈는 yml 설정 파일의 기입한 내용을 도커 CLI로 번역하는 역할을 수행합니다. 네트워크는 따로 지정하지 않아도 default 네트워크로 생성되기 때문에 여러개의 도커 컨테이너를 관리할 때 도커 컴포즈 사용은 많은 장점이 있습니다.
도커 컴포즈 파일의 구성
- Services(required)
- 실행하려는 컨테이너들을 정의하는 역할을 합니다. 이름, 이미지, 포트 맵핑, 환경 변수, 볼륨 등의 내용을 포함하여 컨테이너를 생성하고 관리합니다.
1 2 3 4 5 6 7 8 9 10
image: 컨테이너를 생성할 때 쓰일 이미지 지정 build: 정의된 도커파일에서 이미지를 빌드해 서비스의 컨테이너를 생성하도록 설정 environment: 환경 변수 설정, docker run 명령어의 --env, -e 옵션과 동일 command: 컨테이너가 실행될 때 수행할 명령어, docker run 명령어의 마지막에 붙 는 커맨드와 동일 depends_on: 컨테이너 간의 의존성 주입, 명시된 컨테이너가 먼저 생성되고 실행 ports: 개방할 포트 지정, docker run 명령어의 -p와 동일 expose: 링크로 연계된 컨테이너에게만 공개할 포트 설정 volumes: 컨테이너에 볼룸을 마운트함 restart: 컨테이너가 종료될 때 재시작 정책 no: 재시작 되지 않음 always: 외부에 영향에 의해 종료 되었을 때 항상 재시작 (수동으로 끄기 전까지) on-failure: 오류가 있을 시에 재시작
- 실행하려는 컨테이너들을 정의하는 역할을 합니다. 이름, 이미지, 포트 맵핑, 환경 변수, 볼륨 등의 내용을 포함하여 컨테이너를 생성하고 관리합니다.
- Version(options)
- 이전 버전과의 호환성을 위해 정의 됩니다.
- Networks
- Volumes
- Configs
- Secrets
도커 컴포즈 명령어 & 옵션
docker-compose
1
2
3
up : 도커 컴포즈 파일로, 컨테이너를 생성하기
-f : 도커 컴포즈 파일 지정하기 (지정하지 않아도 자동으로 docker-compose.yml을 찾음)
-d : 백그라운드에서 실행하기
도커를 활용하는 클라우드 서비스는 뭐가 있을까?
클라우드 서비스를 확인하기 앞서 컨테이너 오케스트레이션을 알아보겠습니다.
컨테이너 오케스트레이션
컨테이너 기술은 애플리케이션을 가볍게 패키징하고 이식성을 높여주는 장점이 있지만, 다수의 컨테이너를 관리하고 운영하는 것은 어렵고 복잡한 작업입니다. 이를 해결하기 위해 컨테이너 오케스트레이션 도구들이 생겨났습니다.
컨테이너 오케스트레이션은 여러개의 컨테이너를 자동으로 배치/관리/확장/조정 하는 프로세스
를 말합니다. 대표적인 컨테이너 오케스트레이션은 아래와 같습니다.
- GCP의 GKE(Google Kubernetes Engin)
- AWS의 EKS(Elastic Kubernetes Service), ECS(Elastic Container Service)
컨테이너 오케스트레이션 기능
컨테이너 오케스트레이션이 제공하는 기능을 살펴보겠습니다.
- 컨테이너 클러스터링
- 여러개의 컨테이너를 함께 그룹화하여 하나의 시스템처럼 동작하도록 하여 자원을 효율적으로 활용하는 기능입니다.
- 컨테이너를 실행하는 호스트의 자원을 효율적으로 분배하고 컨테이너가 안정적으로 실행되도록 합니다.
- 서비스 디스커버리
- 컨테이너를 자동으로 발견하고 서비스 이름과 IP 주소등을 관리하여 애플리케이션 간의 연결을 관리하는 기능입니다.
- 클라우드 환경에서의 컨테이너 생성/배치/이동에 따른 IP, PORT 정보를 업데이트하고 관리합니다.
- 오토 스케일링
- 애플리케이션 트래픽 양에 따라 자동으로 컨테이너 수를 조절하여 자원 사용량을 최적화하고 가용성을 보장합니다.
- 로드 밸런싱
- 여러 대의 노드에서 실행 중인 컨테이너들을 조절하여, 트래픽을 균등하게 분배합니다.
- 롤아웃 & 롤백
- 새로운 버전의 애플리케이션을 롤아웃하고 이전 버전으로 롤백하는 기능입니다.
- 자동 복구
- 컨테이너나 노드의 장애 시 자동으로 복구하는 기능입니다.
- 모니터링 & 로깅
- 컨테이너나 노드의 상태를 모니터링하고 로그를 수집하여 애플리케이션 성능과 문제점을 분석하는 기능입니다.
- 보안과 네트워크 관리
- 컨테이너와 노드의 보안을 관리하고, 네트워크 설정을 관리하는 기능
여기서 노드는 컨테이너 클러스터링 환경에서 컨테이너들이 실행되는 물리 / 가상화된 서버를 뜻합니다.
컨테이너 오케이션 툴/서비스
- 도커 스웜
- 쿠버네티스가 등장하기 전까지 가장 대중적인 컨테이너 오케스트레이션 도구 중 하나로 설정이 쉽고 간단하게 작동합니다.
- 쿠버네티스
- 구글에서 Gmail, Youttube 등 다양한 웹서비스의 대용량 트래픽을 감당하기 위해 시작한 프로젝트입니다.
- 오픈소스 기반이고 현재 리눅스 재단에 의해 관리되고 있습니다.
- 대규모에 적합합니다.
- Reeplication Controller로 컨테이너 수를 동적으로 조절하여 스케일링 기능을 강화하였습니다.
- DNS 기반으로 서비스 디스커버리 기능을 강화하였습니다.
- VM 환경, Public Cloud 등 다양한 환경에서 작동되도록 설계되어 있습니다.
- GKE(Google Kubernetes Engine)
- GCP에서 제공하는 쿠버네티스 기반의 관리형 컨테이너 오케스트레이션 서비스입니다.
- 쿠버네티스를 기반하기 때문에 쿠버네티스의 기능을 모두 제공합니다.
- EKS(Amazon Elastic Kubernetes Service)
- AWS에서 제공하는 관리형 쿠버네티스 서비스입니다.
- 사용자는 쿠버네티스API를 사용하여 EKS클러스터를 관리할 수 있습니다.
- ECS(Amazon Elastic Container Service)
- AWS에서 제공하는 관리형 컨테이너 오케스트레이션 서비스입니다.
- 도커 컨테이너를 실행하기 위한 기능 제공합니다.
- 사용자는 ECS를 사용하여 컨테이너를 배포, 관리, 스케일링 할 수 있습니다.
ECS(Amazon Elastic Container Service)
ECS 서비스 종류를 살펴보겠습니다.
EC2
- 컨테이너가 운영되는 자원이 AWS EC2인 유형입니다.
- 용량공급자가 컴퓨팅 자원을 EC2인스턴트를 통해 용량을 공급합니다.
- ECS에서 제공하는 관리형 지표 “CapacityProviderReservation”에 따라 EC2를 용량을 추가/제거 할 수 있으며, 컨테이너의 숫자의 증가/축소에 따라 EC2도 함께 증가/축소하게 됩니다.
- EC2 유형의 비용: 호스트로 사용하는 EC2요금만 과금합니다.
Fargate
- 서버리스 유형으로,EC2를 배포하거나 관리할 필요 없이 그냥 서비스만 운영합니다.
- 컨테이너가 어디서 운영되는지 관리할 필요가 없습니다.
- Fargate 유형의 비용: 시간당 vCPU, Storage 용량 비용이 부과됩니다.
External
- AWS인프라가 아닌 호스트에서 ECS에서 정의한 서비스입니다.
- 호스트&컨테이너 등 실제 서비스는 물리적으로 AWS 밖에서 동작합니다.
- AWS콘솔에서 관리합니다.
ECS 구성
Task Definition
- ECS에서 컨테이너를 실행하기 위한
블루프린트
또는레시피
입니다.- 어플리케이션이 어떻게 실행될지 세부 사항을 포함하고 있습니다.
- 도커 이미지, 필요한 CPU/메모리, 환경변수, 포트 맵핑 등의 내용이 있습니다.
Task
- Task Definition에 기반하여 실행되는 컨테이너 인스턴스입니다.
- Task는 Task Definition이라는 설계도를 기반으로 만들어진 인스턴스라고 볼 수 있습니다.
- 1개의 Task Definition으로부터 여러개의 Task가 실행이 가능합니다.
- 각 Task는 독립적으로 실행되기 때문에 각자의 상태와 라이프 사이클을 가집니다.
Service
- 특정 Task Definition에 기반한 작업 집합을 실행하고 유지 관리하는 역할을 합니다.
- Desired Count
- 사용자가 지정한 수의 작업 인스턴스를 지속적으로 실행하도록 보장합니다.
- 만약 작업 인스턴스가 실패하거나 중지되면 ECS는 자동으로 새 작업을 시작하여 원하는 수의 작업을 유지합니다.
- Load Balancing
- Application Load Balancer, Network Load Balancer 또는 Classic Load Balancer와 통합될 수 있습니다.
- 트래픽이 ECS 작업에 균일하게 분산될 수 있도록 합니다.
- Service Discovery
- 동적 IP 주소를 사용하여 서비스를 검색하고 연결합니다.
- Rolling Updates
- Task Definition을 업데이트하면서 서비스를 지속적으로 실핼할 수 있도록 합니다.
- Scaling
- 요구사항 / 정책에 따라 자동으로 확장 및 축소 시킵니다.
- ECS Cluster
- 컨테이너화된 애플리케이션을 실행하기위한 논리적인 그룹핑 또는 환경을 의미합니다.
- 하나 이상의 인스턴스와 함께 실행되는 서비스 및 Task로 구성됩니다.
- Desired Count