[Kubernetes] 쿠버네티스에서 POD(파드)? 그리고 POD 생성하기

 

l  Kubernetes

 

파드(Pod) 쿠버네티스에서 생성하고 관리할 있는 배포 가능한 가장 작은 컴퓨팅 단위이다. 도커가 가장 일반적으로 알려진 컨테이너 런타임이지만, 쿠버네티스는 도커 외에도 다양한 컨테이너 런타임을 지원한다.

 

파드는 하나 이상의 컨테이너의 그룹이며 스토리지 네트워크를 공유하고, 해당 컨테이너를 구동하는 방식에 대한 명세를 갖는다. 파드의 컨텐츠는 항상 함께 배치되고, 스케줄되며, 공유 컨텍스트에서 실행된다. , 파드는 공유 네임스페이스와 공유 파일시스템 볼륨이 있는 컨테이너들의 집합과 비슷하다.

 

파드는 애플리케이션의 "논리 호스트" 모델링한다. 여기에는 상대적으로 밀접하게 결합된 하나 이상의 애플리케이션 컨테이너가 포함된다. 클라우드가 아닌 컨텍스트에서, 동일한 물리 또는 가상 머신에서 실행되는 애플리케이션은 동일한 논리 호스트에서 실행되는 클라우드 애플리케이션과 비슷하다.

 

애플리케이션 컨테이너와 마찬가지로, 파드에는 파드 시작 중에 실행되는 초기화 컨테이너가 포함될 있다. 클러스터가 제공하는 경우, 디버깅을 위해 임시 컨테이너를 삽입할 수도 있다. 쿠버네티스에서는 이러한 파드를 생성하기 위한 방법으로 kubectl run, kubectl create, kubectl apply 3가지가 있다. 각의 특징에 대해서 알아본다.

 

[kubectl run]

kubectl run kubernetes 클러스터에서 파드나 작업을 생성하는 명령어이다. 가장 간단하게 pod 만드는 방식이며, 실행 명령어 뒤에 각종 옵션 정보를 입력해서 생성한다. 가장 간편한 실행 방법인 반면 입력 정보가 남지 않기 때문에 재실행 문제가 발생했을 원인을 찾거나 해결 방법을 공유하는 등의 어려움이 있다. 일반적인 개발 단계에서 간편하게 pod 생성할 유용하지만 많은 옵션을 함께 사용해야 경우 모든 명령어를 입력해야하기 때문에, yaml 작성하여 사용하는 것이 일반적이다. 기본 구조는 아래와 같다.

Kubectl run [파드이름] –image=[이미지 이름]

 

아래 예시는 파드 생성시 실행할 이미지를 지정한다.

kubectl run nginx --image=nginx

 

아래 예시는 실행할 파드의 개수를 지정한다. Nginx 이미지를 사용하여 3개의 파드를 생성한다. 파드가 중간에 삭제되면 지정한 개수만큼 파드가 유지되도록 파드가 자동 생성된다.

kubectl run nginx --image=nginx --replicas=3

 

아래 예시는 파드를 생성할 포트 번호를 노출시킨다.

kubectl run nginx --image=nginx --port=80

 

아래 예시는 파드를 생성할 다양한 환경변수를 대입하여 파드를 실행한다.

kubectl run my-proxysql --image=my-proxysql --port=6033 --image-pull-policy=Never --restart=Never --env PROXY_ADMIN_PWD=pwd --env PROXY_ADMIN_ID=id

 

 

[kubectl create]

Kubectl create 명령은 kubernetes에서 새로운 리소스를 생성할 사용한다. 명령을 사용하면 yaml파일을 생성하지 않고도 명령어 자체에서 리소스를 생성할 있다. 기본구조는 아래와 같다.

kubectl create [리소스 종류] [리소스 이름]

 

아래 예시는 Nginx 이미지를 사용하는 my-nginx라는 pod 리소스를 생성한다.

kubectl create pod my-nginx --image=nginx

 

아래 예시는 Nginx 이미지를 사용하는 my-deployment 이름을 가진 Deployment 리소스를 생성한다.

Kubectl create deployment my-deployment --image=nginx

 

아래 예시는 80포트를 8080으로 매핑하는 my-service라는 이름의 ClusterIP 서비스 리소스를 생성한다.

Kubectl create service clusterip my-service --tcp=80:8080

 

아래 예시는 key1=value1, key2=value2 데이터를 가진 my-config 이름을 가진 ConfigMap 리소스를 생성한다.

kubectl create configmap my-config --from-literal=key1=value1 --from-literal=key2=value2

 

아래 예시는 password=1234데이터를 가진 my-secret 이름의 secret 리소스를 생성한다.

Kubectl create secret generic my-secret --from-literal=password=1234

 

아래 예시는 리소스를 생성하지 않고 생성 결과만 미리 확인한다.

kubectl create deployment my-deployment --image=nginx --dry-run

 

아래 예시는 파일(yaml 또는 json) 사용하여 리소스를 생성한다.

kubectl create -f test.yaml

 

아래 예시는 리소스가 생성될 네임스페이스를 지정한다.

Kubectl create deployment my-deployment --image=nginx -n my-namespace

 

아래 예시는 컨테이너의 재시작 정책을 지정한다. 상태는 Always, OnFailure, Never 하나를 사용한다.

Kubectl create pod my-pod --image=nginx --restart-policy=OnFailure

 

 

[kubectl apply]

kubectl apply kubectl create 동일하지만 가장 차이점은 기존에 동일한 pod 없다면 새로운 pod 생성하고, 이미 동일한 pod 존재하는 경우 기존 config 비교하여 수정된 부분만 업데이트 한다.

 

 

[kubectl delete]

파드나 리소스를 삭제하기 위해서는 kubectl delete 명령을 사용한다. 기본 구조는 아래와 같다.

Kubectl delete [리소스 유형] [리소스 이름]

 

아래 예시는 nginx라는 파드를 삭제한다.

kubectl delete pod nginx

 

삭제할 다양한 옵션을 함께 사용할 있다.

l  --all : 모든 리소스를 삭제

l  --force : 강제로 삭제

l  ---grace-period=<second> : 대기시간() 이후 삭제 설정

l  --timeout=<second> : 명령이 실행될 대기할 최대 시간() 설정

 

 

 

2023-09-08 / Sungwook Kang / https://sungwookkang.com

 

 

Kubernetes, 쿠버네티스, pod, 파드, kubectl, create, delete, apply, 파드생성, 리소스 생성

[kubernetes] minikube에서 로컬 docker image 사용하기

 

l  Kubernetes, Docker

 

일반적으로 로컬 컴퓨터에서 쿠버네티스(Kubernetes) 테스트할 minikube 환경을 많이 사용한다. 도커 데스크탑(docker desktop) 설치된 환경에서도 쿠버네티스를 활성화하면 minikube 활성화되어 동작한다. 이러한 환경에서 kubectl run 또는 yaml 파드를 생성할 , 로컬의 이미지를 사용할 경우 이미지를 가져올 없다는 오류와 함께 파드가 생성된 종료된다. 이번 포스트에서는 minikube 환경에서 로컬의 docker image 사용하여 파드를 생성하는 방법을 알아본다.

 

로컬의 docker images에서 커스텀 빌드된 이미지 proxysql 있다.

 

로컬의 도커 이미지를 사용하여 파드를 생성하면 오류가 발생한다.

kubectl run my-proxysql --image=proxysql

 

 

오류를 살펴보면 ErrImagePull이라는 상태 메시지를 있는데, 상태를 자세히 확인하기 위해 kubectl describe 명령을 사용하여 상세 메시지를 확인한다.

kubectl describe pods my-proxysql

 

 

마지막에 오류 메시지를 보면, 이미지를 가져올 없어 발생한 오류라는 것을 확인할 있다.

Failed to pull image "proxysql": rpc error: code = Unknown desc = Error response from daemon: pull access denied for proxysql, repository does not exist or may require 'docker login': denied: requested access to the resource is denied

 

일반적으로 생각할 , 쿠버네티스를 사용하여 파드를 생성하면, 로컬의 이미지를 사용할 알았는데 그렇지 않다. 그래서 minikube에서 로컬의 이미지를 사용할 있도록 minikube 도커를 연결해야해는데, 다행히 쿠버네티스에서는 공식적으로 이러한 부분을 지원하고 있다.

 

아래 명령어를 사용하면, 현재 minikube에서 도커 host 연결할 있는 방법을 알려준다. 결과 정보를 바탕으로 일일이 등록해도 되지만, 마지막줄에서 도커 호스트와 한번에 연결할 있는 명령어를 제공하기 때문에 그대로 복사해서 사용할 있다.

minikube docker-env

 

 

마지막 줄의 명령어를 실행하여 minikube에서 docker host 연결한다.

eval $(minikube -p minikube docker-env)

 

명령어실행 도커에서 컨테이너를 조회해 보면 쿠버네티스의 컨테이너가 조회되는 것을 확인할 있다.

 

지금부터는 docker 이미지가 minikube에서 동작하는 driver(docker) 연결되었기 때문에 이제부터 생성되는 docker image minikube 위에 생성하게 된다.

 

다시 한번 이미지를 빌드 한다. 이번에는 이전과 차별을 두기 위해 my-proxysql 이라는 이름으로 이미지를 생성하였다.

docker build -t my-proxysql .

 

아래 명령을 사용하여 minikube 이미지 목록을 확인한다. 방금 빌드한 이미지 목록을 확인할 있다.

minikube image ls --format table

 

 

아래 명령을 사용하여 파드를 실행한다. 이때 로컬의 이미지를 사용하도록 --image-pull-policy=Never 옵션을 함께 사용한다. 정상적으로 파드가 실행중인 것을 확인할 있다.

kubectl run my-proxysql1 --image=my-proxysql --image-pull-policy=Never --restart=Never

 

 

 

[참고자료]

l  https://minikube.sigs.k8s.io/docs/handbook/pushing/#1-pushing-directly-to-the-in-cluster-docker-daemon-docker-env

l  https://www.baeldung.com/docker-local-images-minikube

l  https://egkatzioura.com/2020/03/08/use-local-docker-image-on-minikube/

 

 

 

2023-09-07 / Sungwook Kang / https://sungwookkang.com

 

 

도커파일, dockerfile, minikube, Kubernetes, 로컬이미지 사용, 파드생성, pod create, 도커이미지

[Docker] 컨테이너실행시 sh 스크립트 호출과 매개변수 사용

 

l  Docerk, Shell script

 

Dockerfil 제작하면서, 컨테이너 실행시 특정 스크립트를 실행할 , 스크립트 실행에 필요한 파라메터 값을 받아오지 못하는 문제가 있었다. (도커의 문제가 아닌 나의 코드 오류 문제) 단독으로 스크립트를 실행하면 정상적으로 실행되는데, 유독 컨테이너 실행시에만 값을 받지 못하였다. 해결 방법은 매우 간단하게 Dockerfile에서 사용한 ENV 환경변수를 그대로 스크립트에서 사용하면 되는거였다. (너무 어렵게 생각해서 문제를 해결하지 못한 것이었다.)

 

[잘못된 예시]

abc.sh에서 인풋 변수로 값을 사용할 있도록 read 명령어를 사용하였으며, 해당 변수로 받은 값을 출력하려고 작성.

abc.sh
#!/usr/bin/env bash
 
read var1
read var2
 
echo $var1
echo $var2

 

컨테이너 실행시 ENTRYPOINT에서 abc.sh 실행하면서 파라메터를 전달하려고 작성.

Dockerfile
FROM ~~~~
 
ENV sh_var1 var1_value
ENV sh_var2 var2_value
 
ENTRYPOINT [“abc.sh”, “$sh_var1”, “$sh_var2”]

 

 

[정상 예시]

abc.sh
#!/usr/bin/env bash
 
#read var1 <- 인풋 변수 삭제
#read var2 <- 인풋 변수 삭제
 
echo $sh_var1 #<- dockerfile ENV 변수를 그대로 가져다 사용
echo $sh_var2 #<- dockerfile ENV 변수를 그대로 가져다 사용

 

Dockerfile
FROM ~~~~
 
ENV sh_var1 var1_value
ENV sh_var2 var2_value
 
ENTRYPOINT [“abc.sh”] #<- ENTRYPOINT호출시 sh 파일만 실행

 

 

물론 방법 외에도 다양한 사용법이 있을텐데, 우선 나의 코드에서는 각각의 변수를 호출해서 사용하려고 해서 발생한 문제로, 도커파일과 스크립트간의 매개변수 전달에 대한 이해가 부족해서 발생한 문제였다.

 

 

 

 

2023-09-07 / Sungwook Kang / https://sungwookkang.com

 

 

도커파일, dockerfile, 쉘스크립트, shell script, 매개변수, 도커환경변수, docker env, shell read

[Kubernetes] 쿠버네티스에서 파드 생성시 프라이빗 레지스트리 이미지 사용하기

 

l  Kubernetes

 

Kubernetes 환경에서 pod 생성할 Private Registry에서 이미지를 다운받아 실행하는 방법에 대해서 알아본다.

 

현재 구성되어 있는 실습 환경은 MAC OS + PODMAN + MINIKUBE이다. 일반적으로 많이 사용하는 docker 환경은 아니지만 사용법이 거의 유사하기 때문에 따라하는데 크게 문제가 없으리라 생각한다. Minikube 설치 Podman 설치는 공식 문서에 쉽게 설명되어 있기 때문에 여기에서는 다루지 않는다.

 

l  Podman Installation Instructions : https://podman.io/docs/installation

l  minikube start : https://minikube.sigs.k8s.io/docs/start/

 

실습 시나리오는 아래와 같다.

1.       Dockerfile 작성

2.       컨테이너 이미지 빌드

3.       Docker Hub 개인 저장소에 이미지 푸시

4.       쿠버네티스에서 프라이빗 시크릿키 생성

5.       YAML 파일 작성

6.       Pod 생성

 

사용자 커스텀 이미지를 만들기 위해 Dockerfile 작성한다. Dockerfile 작성에 관한 방법은 다른 문서를 참고한다. 도커 허브의 공식 이미지 저장소에서는 Dockerfile 대한 샘플코드를 제공한다. 아래는 proxysql 공식 저장소이다.

l   https://hub.docker.com/r/proxysql/proxysql

 

 

 

 Dockerfile 작성이 완료되었으면, 이미지를 빌드 한다. Podman 명령어는 도커 명령어와 거의 유사하기 때문에 어려움 없이 사용할 있다. 아래 스크립트는 Dockerfile 빌드하여 컨테이너 이미지를 생성하고, 현재 생성되어 있는 이미지를 확인한다.

podman build -t proxysql-sw:1.0.0 .
 
podman images

 

 

 

podman에서는 도커 레지스트리에 push하기 위해 로그인 과정이 필요하다. 도커 허브의 로그인은 아래와 같은 명령어를 사용한다. 로그인은 ID, 패스워드로 인증한다.

podman login docker.io

 

 

 

이미지를 푸시 하기 위해서는 이미지 ID 필요하다. Podman images명령을 사용하여 확인한 이미지ID 사용하여 도커 허브의 프라이빗 레지스트리로 푸시 한다.

podman push 561f3e4999fddocker.io/<개인저장소 경로>

 

 

쿠버네티스에서 파드 생성시 사용할 프라이빗 레지스트리에 대한 시크릿 키를 생성한다. 시크릿 키에 대한 생성은 여러 방법이 있지만 여기에서는 커맨드 라인에서 자격증명을 통한 시크릿 키를 생성한다. 아래 예제에서는 시크릿 이름은 regcred 생성한다.

kubectl create secret docker-registry regcred --docker-server=<your-registry-server> --docker-username=<your-name> --docker-password=<your-pword> --docker-email=<your-email>

 

l   <your-registry-server> : 프라이빗 도커 저장소의 FQDN 주소로, 도커허브(DockerHub) https://index.docker.io/v1/ 사용

l   <your-name> : 도커 사용자의 계정

l   <your-pword> : 도커 사용자의 비밀번호

l   <your-email> : 도커 사용자의 이메일 주소

 

키가 정상적으로 생성되었는지는 아래 명령으로 확인 가능하다. 명령을 실행하면 키에 대한 자세한 정보를 확인할 있다.

kubectl get secret regcred --output=yaml

 

 

쿠버네티스에서 파드 생성시 사용할 YAML 파일을 작성한다. YAML에서 시크릿 키를 사용할 있도록 imagePullSecrets 항목에서 시크릿키 이름을 입력한다.

apiVersion: v1
kind: Pod
metadata:
  name: private-reg
spec:
  containers:
  - name: private-reg-container
    image: <your-private-image>
  imagePullSecrets:
  - name: regcred

 

 

YAML파일을 사용하여 쿠버네티스 파드를 생성한다.

kubectl apply -f my-private-reg-pod.yaml

 

 

도커허브의 개인 저장소 이미지를 사용하여 파드가 정상적으로 생성된 것을 확인할 있다.

kubectl get pod 

 

 

 

지금까지 도커 허브의 프라이빗 레지스트리에서 이미지를 받아 파드를 생성하는 방법에 대해서 알아보았다. 원래 나의 목적은 로컬( 컴퓨터)에서 이미지를 빌드한 다음 로컬 저장소의 이미지를 사용하여 쿠버네티스 파드를 생성하려고 하였는데, podman에서 생성한 이미지를 minikube에서 찾지 못하여 (정확히는 내가 모르는 ) 도커 허브를 사용하는 방향으로 실습하였다. 이후 작업으로 로컬 저장소에서 파드를 생성하는 방법을 추가적으로 알아볼 예정이다.

 

 

[참고자료]

l  Podman Installation Instructions : https://podman.io/docs/installation

l  minikube start : https://minikube.sigs.k8s.io/docs/start/

l  docker hub : https://hub.docker.com/

l  프라이빗 레지스트리에서 이미지 받아오기 : https://kubernetes.io/ko/docs/tasks/configure-pod-container/pull-image-private-registry/

 

 

 

 

2023-08-09 / Sungwook Kang / https://sungwookkang.com

 

 

쿠버네티스, Kubernetes, 미니쿠베, minikube, 도커, 도커허브, 컨테이너, 도커파일, dockerfile, yaml, 도커 레지스트리, 프라이빗 레지스트리, podman, 파드맨, 도커빌드. 이미지빌드

[Kubernetes] vagrant 환경에서 Kubernetes 클러스터 구성하기

 

l  Kubernetes on vagrnat

 

vagrant에서 Kubernetes 클러스터를 구성하는 방법에 대해서 알아본다. 클러스터 구성환경은 virtualbox centos8 운영체제의 가상머신을 3 생성하고, 머신은 master, woker1, woker2 구성한다.

 

l  vagrant 활용한 개발 환경 구축하기 : https://sungwookkang.com/1523

l  vagrant 가상머신 생성하기 : https://sungwookkang.com/1524

 

호스트이름 IP 역할
k8s-master 192.168.10 Master node
k8s-worker1 192..168.11 Worker node
k8s-worker2 192.168.12 Worker node

 

l   Kubernetes Version : v1.27.3

l   Docker Version : 24.0.2, build cb74dfc

 

vagrnatfile 구성 Kubernetes 구성에 사용할 스크립트 파일은 아래 깃헙을 참고 한다.

l   https://github.com/sqlmvp/k8s-cluster-vagrant

 

 

vagrant up 완료되면 아래와 같이 클러스터가 생성되어 ready 상태로 동작되는 것을 확인할 있다.

 

 

2023-07-03 / Sungwook Kang / https://sungwookkang.com

 

 

vagrant, 베이그랜트, 쿠버네티스, Kubernetes,

[Prometheus] Prometheus Thanos 아키텍처 살펴보기

 

l  Prometheous with Thanos

 

Thanos(타노스) CNCF(https://www.cncf.io/) 인큐베이팅 프로젝트로, 프로메테우스의 확장성과 내구성을 향상시키기 위한 오픈소스 프로젝트이다.

l  Prometheus 확장 내구성을 위한 다양한 구성 방법 : https://sqlmvp.tistory.com/1521

 

Thanos Prometheus 2.0 스토리지 형식을 활용하여 빠른 쿼리 대기 시간을 유지하면서 모든 개체 스토리지에 메트릭 데이터를 효율적으로 저장한다. 또한 운영중인 프로메테우스 서버의 데이터를 통합 저장 외부 저장소에 데이터를 저장할 있기 때문에 보관 기간에 제한이 없고, 단일 쿼리로 전체 프로메테우스 서버의 데이터를 쿼리 있다. 장점을 크게 정리하면 아래와 같이 정리할 있다.

l  Long-term Storage : 원격 스토리지에 데이터를 안정적으로 저장하여 장기적인 데이터 보존을 가능

l  Global Query : 여러 원격 스토리지에서 데이터를 통합하여 조회할 있는 Global Query 기능을 제공하여 분산된 데이터에 대해 단일 쿼리를 실행할 있어 데이터 분석과 모니터링에 유용

l  HA(고가용성) : 원격 스토리지에 데이터를 복제하여 프로메테우스 서버 하나가 장애가 발생하더라도 데이터의 고가용성을 보장

 

타노스는 Sidecar, Query Gateway, Store Gateway, Compactor, Ruler, Receiver라는 6개의 컴포넌트로 이루어져 있다.  

 

l   Thanos Sidecar

ü  Prometheus 함께 하나의 POD 배포되어 기존 프로메테우스 서버와 통합

ü  Prometheus 데이터를 Object Storage 버킷에 백업하고 다른 Thanos 구성 요소가 gRPC API 통해 Sidecar 연결된 Prometheus 인스턴스에 액세스

ü  2시간마다 프로메테우스 메트릭을 객체 스토리지로 보냄

ü  사이드카는 Prometheus 끝점을 사용. --web.enable-lifecycle 플래그로 활성화

l   Thanos Query Gateway

ü  PromQL 처리하는 부분으로 필요한 Prometheus sidecar 연결

ü  질의를 Store (Store API), Sidecar등으로 전달하고 수집

ü  타노스의 전역 쿼리 계층(Global query layer) 사용하여 모든 프로메테우스 인스턴스에 대해 PromQL 사용하여 한번에 조회가능

ü  쿼리 구성 요소는 상태 비저장이며 수평 확장이 가능하며 여러 복제본과 함께 배포 가능

ü  사이드카에 연결되면 주어진 PromQL 쿼리를 위해 어떤 프로메테우스 서버에 접속해야 하는지 자동으로 감지

ü  단일 Thanos 쿼리 엔드 포인트에서 여러 메트릭 백엔드를 집계하고 중복 제거하는 기능을 제공

l   Thanos Store Gateway

ü  Store 같은 개념이며, API Gateway 역할을 하며 오브젝트 스토리지에 접근하는 모든 작업은 Store API 사용

ü  Query, Receive, Ruler 등에 존재

ü  사이드카와 동일한 gRPC 데이터 API 구성되어 있지만 개체 저장소 버킷에서 찾을 있는 데이터로 백업

ü  스토어 게이트웨이는 오브젝트 스토리지 데이터에 대한 기본 정보를 캐싱 하기위해 소량의 디스크 공간을 차지 (타노스 쿼리 저장소 역할)

l   Thanos Compactor

ü  오브젝트 스토리지에 저장된 블록 데이터를 압축하여 저장공간 최적화 작업 진행

ü  개체 저장소를 간단히 스캔하고 필요한 경우 압축을 처리

ü  동시에 쿼리 속도를 높이기 위해 다운 샘플링된 데이터 복세본을 만드는 역할 수행

ü  주기적 배치 작업으로 실행하거나 데이터를 빨리 압축하기 위해 상시 실행 상태로 있음

ü  데이터 처리를 위해 100GB ~ 300GB 로컬 디스크 공간을 제공하는 것이 좋음  

ü  동시성이 보장되지 않으므로 전체 클러스터에서 싱글톤 형식으로 배포하고 버킷에서 데이터를 수동으로 수정할 실행하면 안됨

l   Thanos Ruler

ü  타노스 사이드카가 적용된 프로메테우스의 보존기간이 충분하지 않거나 전체 보기가 필요한 알림 또는 규칙 구성

ü  Thanos 쿼리 구성 요소에 연결하고 Prometheus Alert Record 규칙을 평가

ü  Prometheus Alert Manager 사용하여 Alert 트리거 있음

l   Thanos Receiver

ü  프로메테우스 서버에서 remote_write 통해 메트릭 데이터 수신할 사용

ü  기본 2시간 단위로 TSDB 블록을 만들어 오브젝트 스토리지에 저장

 

 

아키텍처를 살펴보고 요악하면 다음과 같은 활용을 구상해 있다.

l   다수의 프로메테우스 서버를 Global Query view기능을 통해 하나의 인터페이스로 조회 활용

l   Global Query view, 메트릭 duplication 기능으로 프로메테우스 서버가 장애나더라도 서비스 단절이나 데이터 손실 방지

l   외부 저장소를 활용할 있으므로 데이터 크기에 따른 스토리지 성능 하락에 대비할 있고, 메트릭 데이터를 영구 보관할 있으므로 다양하게 활용 가능



 

[참고자료]

l   Thanos공식 문서 : https://thanos.io/v0.6/thanos/getting-started.md/

l   Multi-Cluster Monitoring with Thanos : https://particule.io/en/blog/thanos-monitoring/

 

 

 

2023-06-29 / Sungwook Kang / https://sungwookkang.com

 

 

프로메테우스, Prometheus, 모니터링 시스템, Grafana, 그라파나, DevOps, 데브옵스, Kubernetes, 쿠버네티스, 타노스, Thanos, CNCF

[Prometheus] Prometheus 확장 내구성을 위한 다양한 구성 방법들

 

l  Prometheous with Thanos

 

Prometheus(프로메테우스) 모니터링 시스템은 오픈 소스 기반의 모니터링 시스템으로 Kubernetes(쿠버네티스) 활성화 함께 많이 사용되고 있다.  프로메테우스는 구조가 간단하며, 운영이 쉽고 강력한 쿼리 기능을 가지고 있다. 간단한 텍스트 형식으로 메트릭 데이터를 쉽게 익스포트 있으며, key-value 형식의 데이터 모델을 사용한다. 수집된 데이터는 Grafana(그라파나) 통해 시각화를 제공한다.

 

l  Prometheus 구조 개념 : https://sqlmvp.tistory.com/1520

 

프로메테우스의 가장 약점은 확장성과 가용성이다. 프로메테우스는 클러스터가 지원되지 않는 독립형 서비스로, 프로메테우스 서버 장애시 메트릭을 수집할 없다는 것이다. 프로메테우스 서버의 장애시간 또는 재설정 등으로 서버 또는 서비스가 재시작 동안 타켓에 대한 모니터링을 없다면 이는 서비스를 운영하는데 매우 리스크이다.  이러한 문제를 해결하기 위해 여러가지 프로메테우스 서버 구성에 대한 아키텍처를 생각해 있다.

 

[프로메테우스N 구성으로 타켓 서버 중복 모니터링]

대이상의 프로메테우스 서버를 구성하여, 프로메테우스 서버에서 타겟 서버를 교차해서 메트릭을 수집하는 방식이다.

 

이러한 방식으로 구성할 경우 관리 해야하는 프로메테우스 서버도 증가하지만, 모니터링 대상이 되는 타겟 서버 입장에서도 여러 프로메테우스 서버로부터 요청되는 메트릭 데이터를 수집 전달하기 위해 오버헤드가 발생한다. 또한 프로메테우스로 수집된 데이터를 분석할 때에도, 특정 시점에 장애가 번갈아 발생시, 데이터가 한쪽에만 있게 되므로 중앙에서 한번에 분석하기 불편한 단점이 있다.

 

 

[프로메테우스 Federation 구성]

프로메테우스 서버를 여러 구성하고, 프로메테우스 서버가 다른 프로메테우스 서버로 요청하여 데이터를 수집할 있다.

l  Hierarchical Federation 구성은 프로메테우스 서버 사이에 계층을 두고 Tree 형태로 Federation 구성하는 방법이다. 부모 프로메테우스는 자식 프로메테우스들의 통합 메트릭 제공 통합 메트릭을 기반으로 알람을 제공하는 용도로 사용할 있다.

l  Cross-service Federation 구성은 동일 레벨의 프로메테우스 서버사이를 Federation으로 구성하는 방법이다.

 

 

 

Federation으로 구성할 경우, 프로메테우스 서버는 타겟 서버로부터 일정 주기로 데이터를 수집하고 저장하고, 부모(중앙) 프로메테우스 서버는 프로메테우스 서버로부터 저장된 데이터를 별도의 주기로 수집할 있어, 데이터양이 많을 , 평균값이나 해상도 등을 조정할 있다. 예를들면 프로메테우스 서버는 10 단위로 수집하고, 중앙 프로메테우스는 1 단위로 하위 프로메테우스 서버로 요청하여 평균값 등을 이용할 있다. 하지만 프로메테우스 서버 장애 데이터 유실, 데이터 증가로 인한 중앙 프로메테우스 서버의 오버헤드 증가 문제가 있으므로 일정 규모 이상에서는 적용하기 힘든 부분이 있다.

 

 

[프로메테우스 Thanos 구성]

Thanos 프로메테우스의 확장성과 내구성을 향상 시키기 위한 오픈소스 프로젝트로, 프로메테우스의 메트릭 데이터를 분산된 원격 스토리지에 저장하고 조회할 있는 기능을 제공한다. 아래 그림에서 서드파티 스토리지로 데이터를 저장하기 위한 Adapter 역할이 Thanos 기능이다.

l   Thanos 사용하여 구성 경우 아래와 같은 장점이 있다.

l   Long-term Storage: 원격 스토리지에 데이터를 안정적으로 저장하여 장기적인 데이터 보존을 가능

l   Global Query: 여러 원격 스토리지에서 데이터를 통합하여 조회할 있는 Global Query 기능을 제공하여 분산된 데이터에 대해 단일 쿼리를 실행할 있어 데이터 분석과 모니터링에 유용

l   HA(고가용성): 원격 스토리지에 데이터를 복제하여 프로메테우스 서버 하나가 장애가 발생하더라도 데이터의 고가용성을 보장

 

프로메테우스 Thanos 구성으로 데이터를 수집하여 S3 저장하는 구성하는 구조를 만든다면 아래와 같은 형식으로 아키텍처를 디자인 있다.

1.          Prometheus Thanos 사이드카를 활성화

2.          Sidecar 대화할 있는 기능이 있는 Thanos Querier 배포

3.          Thanos Sidecar S3 버킷에 Prometheus 메트릭을 업로드할 있는지 확인

4.          Thanos Store 배포하여 장기 스토리지( 경우 S3 버킷) 저장된 메트릭 데이터를 검색

5.          데이터 압축 다운 샘플링을 위해 Thanos Compactor 설정

 

 

다양한 구성으로 프로메테우스의 단점인 확장 내구성을 보완하는 방법에 대해서 살펴보았다. 여러 방식이 있겠지만 현재 대규모 서비스에서는 Thanos 구성이 가장 많이 사용되는 하다. Thanos 아키텍처 자세한 내용은 다른 포스트에서 다뤄볼 예정이다. 모니터링을 구성하는데 있어서 정답은 없다. 항상 우리가 가진 리소스 환경에서 가장 최선의 방법을 찾는 것이 중요할 하다.

 

참고자료 :

l   https://wikitech.wikimedia.org/wiki/File:Prometheus_federation.png

l   https://prometheus.io/docs/prometheus/latest/federation/

l   https://www.robustperception.io/federation-what-is-it-good-for/

l   https://aws.amazon.com/blogs/opensource/improving-ha-and-long-term-storage-for-prometheus-using-thanos-on-eks-with-s3/

l   https://thanos.io/v0.6/thanos/getting-started.md/

l   https://particule.io/en/blog/thanos-monitoring/

 

 

 

2023-06-28 / Sungwook Kang / https://sungwookkang.com

 

 

프로메테우스, Prometheus, 모니터링 시스템, Grafana, 그라파나, DevOps, 데브옵스, Kubernetes, 쿠버네티스

[Prometheus] Prometheus 구조 개념

 

l  Prometheous

 

Prometheus(프로메테우스) 모니터링 시스템은 오픈 소스 기반의 모니터링 시스템으로 Kubernetes(쿠버네티스) 활성화 함께 많이 사용되고 있다. 물론 쿠버네티스 환경 외에도 일반적인 온프레미스 환경에서도 사용이 가능하여 많은 인기를 끌고 있다.  현재 CNCF(Cloud Native Computing Foundation) 소속되어 있다.

 

프로메테우스는 구조가 간단하며, 운영이 쉽고 강력한 쿼리 기능을 가지고 있다. 간단한 텍스트 형식으로 메트릭 데이터를 쉽게 익스포트 있으며, key-value 형식의 데이터 모델을 사용한다. 수집된 데이터는 Grafana(그라파나) 통해 시각화를 제공한다.

 

프로메테우스는 순전히 숫자로 시계열을 기록하는 적합하다. 기계 중심 모니터링과 고도로 동적인 서비스 지향 아키텍처 모니터링 모두에 적합하다. 프로메테우스는 중단 중에 신속하게 문제를 진단할 있도록 하는 시스템으로서 안정성을 위해 설계되어있으며, 프로메테우스 서버는 독립형으로 동작하며, 네트워크 스토리지 또는 기타 원격 서비스에 의존하지 않는다.

 

대부분의 모니터링 시스템은 타켓 서버(모니터링 대상 서버) 에이전트를 설치하여 중앙의 모니터링 수집 서버로 push(푸시) 하는 방식인데, 프로메테우스는 pull() 방식을 사용하여 데이터를 수집한다. 모니터링 대상 서버에 exporter(익스포터)라는 에이전트가 실행되어 있으면, 주기적으로 에이전트에 접속하여 데이터를 가져오는 방식이다.

 

l  Jobs / Exporter : 프로메테우스가 모니터링 데이터를 가져갈 있도록 타겟 서버에 설치되는 에이전트 이다. 서버 상태를 나타내는 Node exporter, DB 상태를 나타내는 SQL Exporter 다양한 커스텀 익스포터들이 개발되어 사용되고 있다. 익스포터 자체는 특별한 기능을 수행하지 않는다. 프로메테우스의 요청이 있을 시점에 메트릭을 수집하여 http get 방식으로 리턴한다. 히스토리를 저장하지 않기 때문에 시점의 값만 있다.

l  Pushgateway : Pushgateway는보안상의 이유로 프로메테우스가 직접 익스포터에 연결 없을 , Proxy Forwarding 사용하여 메트릭 데이터를 수집할 있도록 해주는 서비스이다. Application pushgateway 메트릭 데이터를 푸쉬하면, 프로메테우스 서버가 pushgateway 접근해 메트릭 데이터를 하는 방식으로 동작한다.

l  Alertmanager: Alertmanagr 메트릭에 대한 특정 룰을 설정하고 규칙을 위반하는 사항에 대해 알람을 전송하는 역할을 한다. 예를들면 “CPU 사용률이 50% 이상일때 알람을 보낸다.” 라고 룰을 설정하면, 수집된 CPU 메트릭의 값이 50 이상일때 알람을 발송한다.

l  Service discovery : 프로메테우스는 기본적으로 방식을 사용하여 모니터링을 하기 때문에 모니터링 대상 서버의 목록을 유지하고 있어야 한다. 쿠버네티스 환경처럼 오토스케일이 발생할 경우, 타겟 서버의 IP 가변적이어서 수집할 서버의 목록을 확인할 없는 경우가 많다. 이런 경우 모니터링 대상 목록을 관리하기 위해 서비스 디스커버리를 사용하여 유지한다.

l  Retrieval : 익스포터로 부터 주기적으로 메트릭을 수집하는 모듈이며, 서비스 디스커버리 시스템으로 부터 모니터링 대상 목록을 받아오는 역할도 수행하는 컴포넌트이다.

l  HDD/SDD : 수집된 데이터는 프로메테우스 서버의 로컬 메모리와 디스크에 저장된다. 단순하고 사용이 쉬운 방면, 별도의 데이터베이스가 없으므로 확장이 불가능하다.

l  Data visualization : 저장된 메트릭은 PromQL 쿼리 언어를 사용하여 조회가 가능하다. 또한 외부 API 프로메테우스 웹콘솔을 사용하여 visualization 구성할 있다.

 

프로메테우스 서버는 독립적인 구조로 운영되기 때문에, 많은 수의 모니터링 서버에서 대량의 메트릭을 수집할 프로메테우스 서버의 시스템 리소스가 부족할 경우 확장이 불가능한 구조로 되어 있다. 또한 프로메테우스 서버가 다운되거나 설정 변경으로 인한 재시작시 메트릭이 저장되지 않고 유실되는 문제가 있다. 이러한 문제를 수정하기 위해 프로메테우스 서버를 다양한 형태로 구성 운영하기 위한 노하우가 필요 하다. 부분은 다른 포스트에서 다루어 본다.

 

 

 

참고자료 :

https://prometheus.io/docs/introduction/overview/

 

 

2023-06-28 / Sungwook Kang / https://sungwookkang.com

 

 

프로메테우스, Prometheus, 모니터링 시스템, Grafana, 그라파나, DevOps, 데브옵스, Kubernetes, 쿠버네티스

Kubernetes 장점

 

·       Version :

 

 쿠버네티스(Kubernetes) 환경에서는 컨테이너에 애플리케이션에 필요한 모든 항목이 포함되어 있기 때문에 시스템 관리자가 애플리케이션을 실행하기 위해 아무것도 설치할 필요가 없다.

·       애플리케이션 배포 단순화 : 쿠버네티스는 모든 워커 노드를 단일 플랫폼으로 제공하므로 애플리케이션 개발자는 자체적으로 배포할 있으며 클러스터를 구성하는 서버에 대해서 필요가 없다. 특히 특정 컨테이너가  SSD에서만 실행되거나 또는 HDD에서만 실행되어야 하는  경우처럼 특정 리소스가 필요한 경우 쿠버네티스 노드에서 필요한 리소스가 있는 노드를 선택해서 배포할 있다.

·       효율적인 하드웨어 활용 : 쿠버네티스환경에서 애플리케이션을 배포,실행하면 애플리케이션 리소스 요구사항에 따라 사용 가능한 가장 적합한 노드가 선택되어 할당된다. 또한 특정 노드에 애플리케이션을 종속시키지 않는다면 클러스터를 자유럽게 이동할 있어 리소스 가용 상태에 따라 자동으로 이동하거나 매치하여 사용할 있다.

·       자동 복구 모니터링 : 특정 클러스터에 종속되지 않으면 자유롭게 클러스터를 이동할 있기 때문에 이러한 장점으로 인해 모니터링 중에 특정 노드에 장애가 발생하면 자동으로 다른 노드에 애플리케이션이 재배치 되어 실행되기 때문에 야간이나 장애 발생시 즉시 대응할 필요가 없다.

·     오토스케일링 : 쿠버네티스는 애플리케이션에서 사용하는 리소스를 모니터링 하고 애플리케이션에서 실행되는 인스턴스 수를 조정하도록 지시할 있다.

·       개발 환경 단순화 : 애플리케이션이 개발 운영 환경이 동일하기 때문에 개발자는 본인 컴퓨터에서 개발하고 버그를 수정하고, 테스트한 완성된 애플리케이션 환경 그대로 운영 환경에서 실행할수 있다.

 

 

2021-07-30 / Sungwook Kang / https://sungwookkang.com

 

 

Kubernetes, 쿠버네티스

Kubernetes 마스터 노드, 워커 노드

 

·       Version :

 

 쿠버네티스(Kubernetes) 클러스터에서 마스터 노드는 전체 쿠버네티스 시스템을 관리하고 통제하는 쿠버네티스 컨트롤 플레인을 관장한다. 워커 노드는 실제 배포하고자 하는 애플리케이션 실행을 담당한다.

마스터 노드(컨트롤 플레인)에서는 클러스터를 관리하고 클러스터의 기능을 실행한다. 단일 마스터 노드에서 실행하거나 여러 노드로 분할 복제되어 고가용성을 보장할 있는 여러 구성요소로 구성 있다.

·       API Server : 사용자와 컨트롤 플레인과 통신하는 쿠버네티스 API

·       Scheduler : 애플리케이션을 예약하는 스케줄러로, 배포 가능한 구성 요서에 워커 노드 할당을 담당

·       Control Manager : 구성 요소 복제, 워커 노드 추적, 노드 장애 처리 클러스터 기능을 실행

·       etcd : 클러스터 구성을 저장하는 분산 데이터 스토리지  

 

워커 노드는 컨테이너화된 애플리케이션을 실행하는 시스템으로 서비스 실행, 모니터링을 제공한다.

·       Kubelet : API 서버와 통신하고 노드에서 컨테이너를 관리

·       Kube-proxy : 애플리케이션 구성 요소 간에 네트워크 트래픽을 분산하는 쿠버네티스 서비스 프록시

 

 

2021-07-28 / Sungwook Kang / https://sungwookkang.com

 

 

Kubernetes, 쿠버네티스, 마스터 노드, 워커 노드, 컨트롤 플레인, Control Plane

'SW Engineering > DevOps, SRE' 카테고리의 다른 글

[Prometheus] Prometheus 구조 및 개념  (0) 2023.06.28
Kubernetes 장점  (0) 2021.07.31
SRE (Site Reliability Engineering) 역할  (0) 2020.05.14
SRE (Site Reliability Engineering)  (0) 2020.05.11
Docker Network  (0) 2019.03.27

SRE (Site Reliability Engineering) 역할

 

SRE(Site Reliability Engineering) 조직이 해당 시스템, 서비스 제품에서 적절한 수준의 안정성을 달성하도록 지원하는 엔지니어링 분야로,  실패 비용을 줄임으로써, 신속하게 올바른 방향으로 이동할 있도록 지원한다. 과정에서 SRE 자동화, 수치화, 프로세스화를 진행한다. 특히 SRE 관점은 근본적인 문제는 소프트웨어의 문제라고 정의하고 접근한다. SRE 하는 일은 크게 5가지 정도로 나누어 있다.

 

[Metric & Monitoring]

모니터링 지표를 정의하고, 정의된 지표를 모니터링 시스템으로 구성한다. 인사이트를 통해 시스템이 안정적인 상황과 또는 장애가 나는 지표는 무엇인지, 왜인지? 그리고 이러한 지표를 어떻게 개선할 있는지를 고민한다.기본적으로 SRE에서 가장 중요한 부분은 모든것을 데이타화하고, 의사결정을 데이타를 기반으로 한다는 것이다.

 

[Capacity Planning]

시스템을 운영하는데 필요한 하드웨어 리소스(서버, CPU,메모리,디스크,네트워크 ) 확보하는 작업을 진행한다. 수집된 데이터를 통해 서비스 안정성에 필요한 하드웨어를 미리 예측하는 것이다. SRE 엔지니어는 자원 활용의 효율성 측면에서 소프트웨어의 성능을 그리고 안정성 측면에서 소프트웨어의 안정성을 함께 있어야 한다.

 

[Change Management]

대부분의 시스템 장애의 원인은 대략 70% 시스템에 변경을 주는 경우에 발생한다. SRE 점진적인 배포와 변경을 관리한다.배포 또는 장애시 빠르고 정확하게 해당 문제를 찾아낼 있도록 해야하며 마지막으로 문제가 발생하였을때 빠르게 롤백할 있도록 해야한다.

 

[Emergency Response]

일반적으로 장애 복구 단계에서 사람이 직접 매뉴얼로 복구를 하게 되면 장애 복구 시간이 많이 소요된다. 사람이 컨트롤을 하되 가급적이면 단계는 자동화 되는게 좋으며, 사람이 해야 하는 일은 되도록이면 메뉴얼화 되어 있는 것이 좋다. SRE 자동화 뿐만아니라 메뉴얼, 프로세스를 함께 제공한다.

 

[Culture]

운영에 필요한 작업뿐만 아니라 SRE 문화를 전반적으로 만들고 지켜나가는 작업을 진행한다.  데이타에 기반한 합리적인 의사결정과 서로 비난하지 않고 장애 원인을 분석하고 이를 예방하는 포스트모템 문화, 그리고 책임을 나눠가지는 문화를 장려하고 선순환 구조를 만들 있도록 해야한다.

 

[참고자료]

·       IO116-Improving Reliability with Error Budgets, Metrics, and Tracing in Stackdriver : https://drive.google.com/file/d/1iOMaYIwlUBiGoG2mf8MFzl3EHy5xGJpq/view

·       Search Reliability Engineering (부제: 지진에도 흔들리지 않는 네이버 검색시스템) : https://www.slideshare.net/deview/216sresearchreliabilityengineering

·       네이버 검색의 SRE 시스템 : https://d2.naver.com/helloworld/2047663

·       SRE(사이트 안정성 엔지니어링) 소개 : https://docs.microsoft.com/ko-kr/learn/modules/intro-to-site-reliability-engineering/

 

 

 

2020-05-13 / Sungwook Kang / http://sungwookkang.com

 

SRE, Site Reliability Engineering, DevOps, 사이트안정성엔지니어링, 사이트신뢰성엔지니어링, 시스템운영, SiteReliability, 서비스운영, 모니터링자동화, 시스템운영자동화

SRE (Site Reliability Engineering)

 

 

사이트 안정성 엔지니어링(SRE, site Reliability Engineering) 조직이 해당 시스템, 서비스 제품에서 적절한수준의 안정성을 지속적으로 달성하도록 지원하는 엔지니어링 분야이다. 여기서 말하는 적절한수준의 안정성은 무엇일까? IT 시스템이 발달할 수록, 나은 안정성을 추구 할수록, 안정성을 높이는 필요한 노력과 리소스( 비용) 빠른 속도로 증가하고 있다. 이를 다르게 표현한다면, 불필요한 안정성 추구는 시간과 돈의 낭비가 발생한다는 것이다. 결론적으로 안정성 수준은 비즈니스 수요에 적절하고 실용적이어야 하는 수준에서 트레이드오프를 해야한다. 예를 들어, 고객이 100% 안정적이지 않은 네트워크(시간의 90% 가동한다고 가정) 통해 연결하는 경우 노력과 비용() 투자하여 서비스가 95% 안정적으로 되도록 하는 것은, 정의상 시간과 돈을 낭비하는것과 같다. “지속적인 달성  이러한 모든 상황에서 사용자가 해야 역할을 의미한다. SRE 지속 가능한 운영방식을 만들고, 신뢰할 있는 시스템을 만든다. 개발자(시스템 사용자) 서비스, 제품을 만든다. 시간이 지나도 지속되는 운영방식을 구현하여, 사람들(개발자, 사용자)들이 업무에 최선을 다할수 있도록 환경을 제공하는것이 정말 중요하다.

 

SRE 역사는 2013 Google에서 Benjamin Treynor 7명의 소프트웨어 엔지니어로 구성된 팀을 이끌면서 프로덕션의 운영환경을 개선하기 위한 프로젝트를 진행하면서 시작되었다. 팀의 목표는 변화를 수용하면서, 동시에 우수한 품질을 최종 사용자에게 제공하는것이다. 구글은 현재 1500 이상의 엔지니어들이 SRE 업무를 수행하고 있다. SRE 프로세스는 이제 Microsoft, Apple, Amazon, Facebook, Twitter 같은 대기업에서도 도입하여 사용하고 있다.

SRE 엔지니어는 운영(OPS)” 관련된 작업을 수행하는데 최대 50% 시간을 소비한다. SRE 관리하는 소프트웨어 시스템은 고도로 자동화 되어 있으며, 자가치유 기능을 가지고 있어야 한다. 그래서 일반적으로 시스템의 자동화 작업에 50% 시간을 소비하며 나머지 50% 운영에 소비한다. 이상적인 SRE 후보자는 시스템 관려 경험을 가진 소프트웨어 엔지니어 코딩 자동화에 숙련된 시스템 관리자들이다.

 

기존의 DevOps SRE 어떻게 다를까? 모니터링을 통한 문제 식별, 자동화라는 목표는 조직 모두 동일하지만, DevOps 개발쪽에 조금 편향되어 있다면, SRE 운영쪽에 조금 편향되어 있다.

 

 

DevOps 개발과 운영조직 각각의 사일로 현상을(내부 이익만 추구하는 부서간 이기주의 현상) 해체하기 위한 문화적인 움직임으로, 하나의 문화로 인식된다. 그래서 역할을 정의할때도, “저는 DevOps 하는 운영자, 또는 개발자 입니다.”라고 표현한다.

 

 

 

SRE 안정성을 위한 엔지니어링으로 DevOps 운영적인 부분을 보완한다. 그래서 SRE 문화라기보다는 하나의 역할이며, 표현할 때에도 저는 SRE 입니다라는 식으로 규범으로 인식한다.

 

 

[참고자료]

·       IO116-Improving Reliability with Error Budgets, Metrics, and Tracing in Stackdriver : https://drive.google.com/file/d/1iOMaYIwlUBiGoG2mf8MFzl3EHy5xGJpq/view

·       Search Reliability Engineering (부제: 지진에도 흔들리지 않는 네이버 검색시스템) : https://www.slideshare.net/deview/216sresearchreliabilityengineering

·       네이버 검색의 SRE 시스템 : https://d2.naver.com/helloworld/2047663

·       SRE(사이트 안정성 엔지니어링) 소개 : https://docs.microsoft.com/ko-kr/learn/modules/intro-to-site-reliability-engineering/

 

 

 

2020-05-10 / Sungwook Kang / http://sungwookkang.com

 

SRE, Site Reliability Engineering, DevOps, 사이트 안정성 엔지니어링

Docker Network

 

·         Version : Docker

 

Docker network 컨테이너에 내부IP 순차적으로 할당하고 컨테이너가 재시작 때마다 부여된 IP 변경될 있다. 내부IP 도커가 설치된 호스트의 내부망에서만 있기 때문에 외부와 통신을 하기 위해 veth* 라는 네트워크 인터페이스를 생성하여 외부와 통신한다.

 

도커가 설치된 호스트에서 ifconfig ip addr같은 네트워크 명령어로 인터페이스를 확인 해보면 실행중인 컨테이너 만큼 veth* 시작하는 인터페이스가 생성된 것을 있다.

·         eth0 : 내부IP 외부로 통신하기 위한 인터페이스로 호스트의 네트워크 이다. Eth0 네트워크가 veth* 시작하는 네트워크와 통신한다.

·         docker0 : veth* 인터페이스와 바인딩되어 호스트의 eth0 인터페이스와 이어주는 역할을 한다.

 

 

도커가 제공하는 기본적인 네트워크는 bridge, host, none, container, ovelay 있다. 도커를 설치하면 기본적으로 docker0 브릿지를 통해 외부와 통신할 있으며 선택에 따라 여러 네트워크 드라이버를 사용할 있다.

 


도커에서 생성되어 있는 네트워크를 확인은 docker network ls 명령어로 확인할 있다.

docker network ls

 

 

[bridge network]

사용자 정의 브릿지를 새로 생성하여 컨테이너에 연결한다. 컨테이너는 연결된 브릿지를 통해 외부와 통신한다. 아래 명령어로 mybrdge라는 네트워크를 생성할 있다.

docker network create --driver bridge mybridge


 



 

docker run또는 create명령어에 --net 옵션의 값을 설정하면 컨테이너가 해당 네트워크를 사용한다.

docker run -it --name container_name --net mybridge nginx

 

서브넷, 게이트웨이, IP할당 임의로 설정하려면 네트워크를 생성할 아래와 같이 옵션을 추가한다. 주의할 점은 --subnet --ip-range 같은 대역 이어야 한다.

Docker network create --drive=bridge \

--subnet=172.72.0.0/16 \

--ip-range=172.72.0,0/24 \

--gateway=172.72.0.1 \

Mybridge

 

run 명령시 --net-alias 옵션을 함께 쓰면 alias이름으로 여러 개의 컨테이너에 접근할 있다.

docker run -it --name container_name1 --net mybridge --net-alias ali01  nginx

docker run -it --name container_name2 --net mybridge --net-alias ali01  nginx

docker run -it --name container_name3 --net mybridge --net-alias ali01  nginx

 

컨테이너 생성이 완료되면 ping 사용해서 컨테이너로 ping 전송되는 것을 확인할 있다. Ping 전달되는 IP 라운드로빈 방식으로 도커 엔진에 내장된 DNS ali01이라는 호스트 이름을 --net-alias dhqtusdmfh ali01 설정한 컨테이너로 변환(resolve)하기 때문이다.

 

[host]

호스트 네트워크는 호스트의 네트워크 환경을 그대로 사용한다. 호스트 머신에서 설정한 호스트 이름을 컨테이너가 상속받기 때문에 컨테이너의 호스트 이름도 무작위 16진수가 아닌 도커 엔진이 설치된 호스트 머신의 호스트 이름을 설정 된다.

docker run -it --name container_name --net host nginx

 

컨테이너의 네트워크를 호스트로 설정할 경우 별도의 포트 포워딩 필요없이 바로 서비스가 가능하다.

 

[none]

어떠한 네트워크도 사용하지 않겠다는 뜻이다. 외부와의 연결이 단절된다.

docker run -it --name container_name --net none nginx

 

[container]

네트워크는 다른 컨테이너의 네트워크 환경을 공유할 있다. 공유되는 속성은 내부 IP, 네트워크 인터페이스의 MAC 주소 등이다. 사용법은 --net container:[컨테이너ID] 이다.

docker run -it --name container_name --net container:container_id nginx

 

[overlay]

여러 도커 데몬 호스트 사이에 분산 네트워크를 만든다. 네트워크는 호스트 특정 네트워크 상단에 위치하여(오버레이) 호스트 서비스 네트워크에 연결된 컨테이너(swarm 서비스 컨테이너 포함) 안전하게 통신할 있다. 도커는 대상 컨테이너간에 패킷 라우팅을 투명하게 처리 한다. swarm 초기화 하거나 docker호스트를 기존 swarm 가입 시키면 해당 도커 호스트에 개의 새로운 네트워크가 생성된다.

·         오버레이 네트워크라 불리는 Ingress swarm 서비스와 관련된 제어 데이터 트래픽을 처리한다. swarm 서비스를 생성하고 사용자 정의 오버레이 네트워크에 연결하지 않으면 기본적으로 ingress 네트워크에 연결된다.

docker network create -d overlay my-overlay

 

독립 실행형 컨테이너가 다른 docker 데몬에서 실행되는 다른 독립 실행형 컨테이너와 통신하기 위해 사용할 잇는 오버레이 네트워크를 만들려면 --attachable 옵션을 사용한다.

docker network create -d overlay --attachable my-attachable-overlay

 

·         브릿지 네트워크라 불리는 docker_gwbrdge 브릿지 네트워크를 만드는것과 동일하게 docker network create 사용하여 사용자 정의 오버레이 네트워크를 만들 있다. 서비스 또는 컨테이너는 한번에 이상의 네트워크에 연결할 있다. 서비스 또는 컨테이너는 각각 연결된 네트워크를 통해서만 통신할 있다.

docker network create \

--subnet 10.11.0.0/16 \

--opt com.docker.network.bridge.name=docker_gwbridge \

--opt com.docker.network.bridge.enable_icc=false \

--opt com.docker.network.bridge.enable_ip_masquerade=true \

docker_gwbridge

 

swarm 서비스와 독립 실행형 컨테이너 모두 오버레이 네트워크에 연결할 있지만 기본 동작 구성 관련 사항은 다르다. 이러한 이유로 오버레이 네트워크에 적용되는 작업, swarm 서비스 네트워크에 적용되는 작업 독립 실행형 컨테이너에 사용되는 오버레이 네트워크에 적용되는 작업으로 나뉜다.

 

모든 swarm 서비스 관리 트래픽은 기본적으로 GCM모드의 AES알고리즘을 사용하여 암호화 된다. Swarm 관리자 노드는 12시간 마다 데이터를 암호화하는데 사용되는 키를 변화시킨다. 오버레이 암호화를 활성화하면 도커는 오버레이 네트워크 연결된 모든 서비스에 대해 IPSEC 터널을 만들어 통신한다.

 

 

[참고자료]

·         Docker Network Overview :  https://docs.docker.com/network/

·         Bridge networks : https://docs.docker.com/network/bridge/

·         Overlay neworks : https://docs.docker.com/network/overlay/

·         Host networks : https://docs.docker.com/network/host/

·         Disable networks : https://docs.docker.com/network/none/

 

 

 

2019-02-20 / Sungwook Kang / http://sqlmvp.kr

 

Docker, docker network, ingress, overlay, container, host, 도커 네트워크, swarm

Docker Compose

-         여러개의 컨테이너를 설정하고 생성하기

 

·         Version : Docker

 

Docker compose 명령은 여러개의 컨테이너 옵션과 환경을 정의한 파일을 읽어 컨테이너를 순차적으로 생성한다. 도커 컴포즈의 설정 파일(docker-compose.yml) run 명령어 옵션을 그대로 사용할 있으며 컨테이너의 의존성, 네트워크, 볼륨, 컨테이너 등을 유동적으로 조절할 있다.  예를 들어 파이썬 프로그램이 구동되는 컨테이너와 데이터를 저장하는 redis 서버,  웹서버 컨테이너를 실행한다고 , 각각의 run 명령어 다양한 옵션으로 컨테이너를 생성하고 테스트하기에는 매우 번거롭다. 이때 도커 컴포즈를 활용하면 편리하다.

 

도커 컴포즈는 컨테이너 설정이 정의된 YAML 파일을 읽어 도커 엔진을 통해 컨테이너를 생성한다.


아래 스크립트는 docker-compose.yml 예제 스크립트이다. YAML 파일에서 들여쓰기 , 도커 컴포즈는 TAP 인식하지 못하기 때문에 2개의 공백(Space) 사용하여 하위 항목을 구분한다.

[docker-compose.yml]

version: "3"

services:

  web:

    # replace username/repo:tag with your name and image details

    image: username/repo:tag

    deploy:

      replicas: 5

      restart_policy:

        condition: on-failure

      resources:

        limits:

          cpus: "0.1"

          memory: 50M

    ports:

      - "80:80"

    networks:

      - webnet

  visualizer:

    image: dockersamples/visualizer:stable

    ports:

      - "8080:8080"

    volumes:

      - "/var/run/docker.sock:/var/run/docker.sock"

    deploy:

      placement:

        constraints: [node.role == manager]

    networks:

      - webnet

  redis:

    image: redis

    ports:

      - "6379:6379"

    volumes:

      - "/home/docker/data:/data"

    deploy:

      placement:

        constraints: [node.role == manager]

    command: redis-server --appendonly yes

    networks:

      - webnet

networks:

  webnet:

·         Version : YAML 파일 포맷 버전

·         Service : 생성될 컨테이너들을 묶어 놓는 단위. 서비스 항목 아래에 컨테이너에 적용될 옵션을 지정

·         Web, visualizer, redis : 생성될 서비스 이름. 항목 아래에 컨테이너가 생성될 필요한 옵션을 지정

·         image : 컨테이너를 생성할 사용될 이미지 이름

·         link : docker run --link 같으며 다른 서비스에서 서비스명만으로 접근할 있도록 설정

·         environment : docker run --env, -e 옵션과 동일. 컨테이너 내부에서 사용할 환경변수 지정

·         command : 컨테이너가 실행될 수행할 명령어를 설정.

·         ports : docker run -p 같으며 컨테이너를 개방할 포트를 설정.

·          

 

도커 컴포즈 관련 옵션은 매우 다양하게 지원되므로 자세한 내용은 공식 문서를 참고 있도록 한다.

·         Get Started with Docker Compose : https://docs.docker.com/compose/gettingstarted/

 

도커 컴포즈로 컨테이너를 생성하는 명령은 docker-compose up -d이다. 어떠한 설정도 하지 않으면 기본적으로 로컬 디렉터리의 docker-compose.yml 파일을 읽어 로컬의 도커 엔진에서 생성한다. 컨테이너 생성이 완료되면 docker ps에서 실행된 컨테이너를 확인할 있다.

docker-compose up -d

 

 

 

 

[참고자료]

·         Get Started with Docker Compose : https://docs.docker.com/compose/gettingstarted/

 

 

2019-02-17 / Sungwook Kang / http://sqlmvp.kr

 

Docker,  dockerfile, docker build, 도커 파일, 도커 이미지 생성, dockerfile reference, docker compose, 도커 컴포즈, 도커 컨테이너, docker container

Docker build

-         Dockerfile 이용해서 이미지 생성하기

 

·         Version : Docker

 

Docker build 명령은 dockerfile 이용해서 이미지를 만드는 작업을 한다. dockerfile에는 이미지 생성시 필요한 작업이 스크립트로 작성되어 있다.

·         dockerfile : http://sqlmvp.kr/221465287824

 

아래 스크립트는 docker build 사용해서 이미지를 생성한다.

docker build -t makeimage:0.0 ./

 

·         -t : 생성될 이미지의 이름을 설정. 스크립트에서는 makeimage:0.0 라는 이름의 이미지가 생성된다. -t 옵션을 사용하지 않으면 16진수 형태의 이름으로 이미지가 생성된다.

·         ./ : build 명령어 끝에는 dockerfile 저장된 경로를 입력한다. 로컬 디렉터리의 dockerfile 사용할 수도 있으며 외부 URL로부터 dockerfile 내용을 가져와 빌드할 있다. 예제에서는 로컬의 현재 디렉터리(./) 입력했다.

 

Build 시작하면 dockerfile 내용이 실행되며 실행 단계가 출력된다.

 


빌드가 완료되면 docker image에서 생성된 이미지를 확인할 있다.

 


docekrfile에서 명령어가 하나씩 실행될 때마다 새로운 컨테이너가 하나씩 생성되며 이미지로 커밋한다. 명령어가 실행될 때마다 이전 스텝의 이미지에 명령어가 실행되고 새로운 이미지 레이어로 저장된다.

[출처 : https://openliberty.io/blog/2018/06/29/optimizing-spring-boot-apps-for-docker.html]

 

dockerfile 만들 주의할 점은 불필요한 작업으로 이미지 사이즈가 커지지 않도록 해야 한다. 예를들어 100MB 크기의 파일을 만들어 컨테이너에 할당하고 다시 삭제하는 명령이 있을때, dockerfiles 이미지를 빌드하면서 단계마다 이미지 레이어를 만드는데,  최종 빌드가 완료된 상태에서 이미지에는 100MB크기의 파일이 존재하지 않지만 이미지의 크기는 기존 이미지에 100MB 더한 크기를 가지고 있다. , 파일을 삭제 했다는 레이어를 가지고 있으므로 실제론 파일이 없더라고 공간은 차지한다. 이러한 현상을 방지하기 위해서는 dockerfile 작성할때 && 기호로 run 명령을 하나로 묶는것이다. 여러개의 명령을 run  하나에서 실행하도록 하면 된다.

FORM ubuntu:14.04

RUN mkdir /test && dummyfile -l 100m /test/dummy && rm /test/dummy

 

만약 다른 사람이 빌드한 이미지에 불필요한 이미지 레이어가 있으면 해당 이미지로 컨테이너를 생성하고  docker export, import 명령어를 사용해 컨테이너를 이미지로 만들면 레이어가 1개로 줄어들어 이미지의 크기를 줄일 있다. 그러나 이전 이미지에 저장된 각종 이미지 설정은 삭제되므로 주의해야 한다.

 

Docker build 다양한 옵션이 있으므로 공식 문서를 참고할 있도록 한다.

·         docker build : https://docs.docker.com/engine/reference/commandline/build/

 

 

2019-02-14 / Sungwook Kang / http://sqlmvp.kr

 

Docker,  dockerfile, docker build, 도커 파일, 도커 이미지 생성, dockerfile reference

Docker file

-         이미지 생성시 필요한 작업을 스크립트로 만들기

 

·         Version : Docker

 

컨테이너를 생성하는 방법은 베이스 이미지를 이용하여 위에 다양한 애플리케이션을 설치하는 방법, 또는 이미 모든 환경이 구성된 컨테이너를 이미지로 만드는 방법 다양하다.

·         Docker Image생성 : http://sqlmvp.kr/221461385385

·         Docker Image 추출 : http://sqlmvp.kr/221463568253

 

이번 포스트에서는  Dockerfile 이용해서 이미지를 생성하는 방법에 대해서 알아본다. Dockerfile 이미지를 생성하기 위해 컨테이너에 설치해야하는 패키지, 추가해야하는 소스코드, 실행시 필요한 명령어, 스크립트 등을 하나의 파일로 생성한 것이다. Build명령을 실행하면 Dockerfile 읽어 이미지를 생성한다. Dockerfile 사용하면 직접 컨테이너를 생성, 커밋, 배포하는 번거로움을 있으며 배포 자동화에 용이하다.

 

도커 엔진에서는 Dockerfile 읽어들일때 기본적으로 현재 디렉터리에 있는 Dockerfile이라는 이름을 가진 파일을 선택한다. 아래 스크립트는 Dockerfile 예시이며 명령의 기능에 대해서 살펴본다.

 


# Use an official Python runtime as a parent image

FROM python:2.7-slim

 

LABEL "purpose"="practice"

 

# Set the working directory to /app

WORKDIR /app

 

# Copy the current directory contents into the container at /app

COPY . /app

 

# Install any needed packages specified in requirements.txt

RUN pip install --trusted-host pypi.python.org -r requirements.txt

 

# Make port 80 available to the world outside this container

EXPOSE 80

 

# Define environment variable

ENV NAME World

 

# Run app.py when the container launches

CMD ["python", "app.py"]

 

Dockerfile 명령은 위에서 아래로 차례대로 실행한다.

·         FROM : 생성할 이미지의 베이스 이미지를 입력한다. 이미지가 로컬에 없다면 자동으로 도커허브에서 pull 한다.

·         LABEL : “:형태로 이미지에 메타데이터 추가. 추가된 메타 데이터는 docker inspect 명령어로 확인가능.

·         WORKDIR : 명령어를 실행할 디렉터리를 나타냄. Bash에서 cd 명령과 동일한 기능이다.

·         COPY : 로컬 디렉터리의 파일을 이미지에 복사하는 역할. ADD 다른 점은 COPY 로컬 디렉터리만 가능하고 ADD 외부 URL tar 파일도 추가 가능하다.

·         RUN : 이미지를 만들기 위해 컨테이너 내부에서 명령어를 실행.

·         EXPOSE : Dockerfile 빌드로 생성된 이미지에서 노출할 포트를 설정

·         CMD : 컨테이너가 시작될 때마다 실행할 명령어(커맨드) 설정, Dockerfile에서 한번만 사용할 있다.

 

위의 예제를 정리해보면 아래와 같다.

Python:2.7-slim 베이스 이미지를 사용하며 생성될 이미지의 라벨은 “purpose=practice” 설정한다. 작업디렉터리를 /app 변경한다음 로컬의 ./app 디렉터리의 내용을 이미지로 복사한다. 그리고 pip inatall명령을 컨테이너 내부에서 실행하고 컨테이너는 80 포트를 사용한다. 마지막으로 python 명령으로 app.py 실행한다.

 

Dockerfile 다양한 명령어를 지원하며 자세한 내용은 아래 링크를 참고 한다.

·         Dockerfile reference : https://docs.docker.com/engine/reference/builder/

 

 

 

 

2019-02-13 / Sungwook Kang / http://sqlmvp.kr

 

Docker,  dockerfile, docker build, 도커 파일, 도커 이미지 생성, dockerfile reference

Docker Image 추출

 

·         Version : Docker

 

지난 포스트에 docker commit 명령을 사용하여 이미지를 생성한 다음 docker hub 사용하여 이미지를 공유하는 방법에 대해서 다루었다.

·         도커 이미지 생성 : http://sqlmvp.kr/221461385385

 

이번 포스트에서는 이미지 파일을 단일 바이너리 파일로 저장하는 방법과 저장된 이미지 파일을 로드 하는 방법에 대해서 살펴본다.

 

 이미지를 파일로 추출하는 명령은 docker save이다. 명령을 사용하면 이미지의 모든 메타 데이터를 포함하는 하나의 파일로 추출할 있다.

docker save [option] image [image]

docker save busybox > busybokx.tar

docker save --output busybox.tar busybox 

docker save -0 fedora-latest.tar fedora:latest

·         --output, -o : STDOUT 대신 파일에 쓰기

 


추출된 이미지는 docker load 명령으로 도커에 다시 로드할 있다. 이미지를 로드하면 이전의 이미지와 동일한 이미지가 도커 엔진에 생성된다.

docker load [OPTION]

docker load < busybox.tar

docker load --input fefora.tar

·         --input, -i : STDIN 대신  tar 아카이브 파일에서 읽기

·         --quiet, -q : 부하 출력 억제

 

 

docker save, load 비슷한 기능을 하는 명령으로 docker export, import 있다.

export 명령은 컨테이너의 파일 시스템을 tar 파일로 추출하고 import 추출된 파일을 이미지로 다시 저장한다. export 명령은 컨테이너와 연관된 볼륨의 내용을 내보내지는 않는다. 볼륨이 컨테이너의 기존 디렉터리 위에 마운트 되면 docker export 볼륨의 내용이 아닌 기본 디렉토리의 내용을 내보낸다.

docker export [OPTIONS] CONTAINER

docker export red_panda > latest.tar

docker export –output=”latest.tar” red_panda

·         --output, -o : SDTOUT대신 파일에 쓰기

 

Import 명령을 사용할 STDIN에서 직접 데이터를 가져오기 위해 URL또는 –(대시) 지정할 있다. URL 파일 시스템이나  Docker 호스트의 개별 파일(.tar, .tar.gz, .tgz, .bˆp, .tar.xz, .txz) 포함하는 아카이브를 가리킬 있다. 아카이브를 지정하면  Docker 컨테이너에서 /(root) 기준으로 아카이브에 압축 해제 한다. 개별 파일을 지정하는 경우 호스트 전체 경로를 지정해야 한다. 원격에서 가져오려면 http://또는 https:// 시작하는 URL프로토콜을 사용한다.

docker import [OPTIONS] file|URL|- [REPOSITORY[:TAG]]

docker import http://example.com/exampleimage.tgz

docker import /path/to/exampleimage.tgz

·         --change, -c : 생성된 이미지에 dockerfile 적용

·         --message, -m : 가져온 이미지에 커밋 메시지 설정

·         --platform : 서버가 멀티 플랫폼 가능하면 플랫폼 설정

 

 

 

[참고자료]

·         docker save : https://docs.docker.com/engine/reference/commandline/save/

·         docker load : https://docs.docker.com/engine/reference/commandline/load/

·         docker export : https://docs.docker.com/engine/reference/commandline/export/

·         docker import : https://docs.docker.com/engine/reference/commandline/import/

 

 

 

2019-02-11 / Sungwook Kang / http://sqlmvp.kr

 

Docker, 이미지 추출, docke save, docker load, docker import, docker export, 도커 로드

Docker Image 생성 docker hub 이미지 업로드

 

·         Version : Docker

 

컨테이너는 기본적으로 이미지를 사용하여 생성하며, 컨테이너 생성 사용자 변경 부분에 대해서는 필요에 따라 새로운 이미지를 만들어서 배포하거나 재사용하기도 한다. 이번 포스트에서는 docker hub에서 이미지를 다운로드 (Pull), 업로드(push) 이미지를 생성(commit)하는 방법에 대해서 알아본다.

 

도커는 기본적으로 docker hub(https://hub.docker.com/)라는 중앙 이미지 저장소에서 이미지를 내려 받는다. 아래 그림처럼 docker hub 도커가 공식적으로 제공하는 이미지 저장소로 누구나 가입 이미지를 내려 받을 있다. 또한 사용자 이미지를 도커 허브에 업로드하여 다른 사람과 공유할 있다.

[출처]  https://www.itzgeek.com/how-tos/linux/working-with-docker-images-building-docker-images.html

 

사용자가 docker create, docker run, docker pull 명령을 실행하면 로컬에 해당 이미지가 없을 경우 docker hub에서 해당 이미지를 검색하여 다운로드 받는다. 대부분의 이미지가 공식적으로 제공되어 있기 때문에 직접 이미지를 만들어 사용하지 않아도 되므로 빠르고 편리하게 개발 운영 환경을 구축 있다. 아래 명령어는 docker hub 이미지가 있는지 확인하는 명령어로 공식 이미지의 경우 “OFFICIAL” 라벨이 부여되어 있으며 “STARS” 해당 이미지가 사용자로부터 얼마나 즐겨찾기가 되었는지를 나타낸다.

docker search nginx

 

 

docker hub 부터 이미지를 다운로드 받으려면 pull 명령을 사용한다.

docker pull nginx

 



베이스 이미지로부터 컨테이너를 생성하고 사용자가 변경 사항을 만들었다면 docker commit 명령을 사용하여 현재 컨테이너를 이미지로 만들 있다. 아무런 옵션을 사용하지 않으면 태그는 자동적으로 “latest” 설정된다. -a 옵션은 작성자를 나타내며, -m 커밋 메시지를 작성한다. 아래 스크립트는 nginx 라는 컨테이너를 nginx_sqlmvp:first 이미지를 생성한다.

docker commit nginx nginx_custom

docker commit -a "sqlmvp" -m "my image" nginx nginx-sqlmvp:first

 

 

로컬에서 생성된 이미지를 공유하려면 리포지토리가 있어야 한다. Docker hub 누구나 가입해서 무료로 리포지토리를 사용할 있다. 무료 계정의 경우 리포지토리가 퍼블릭이며, 유료로 사용할 경우 프라이빗 리포지토리를 이용할 있다. 또한 docker hub외에 프라이빗 리포지토리를 구축해서 사용할 있다. 아래 스크립트는 docker hub 로컬의 이미지를 업로드(push)한다. docker hub 업로드하기 전에 이미지에 리포지토리와 태그를 만들어야 한다.

Syntax : docker tag image username/repository:tag

Ex) docker tag nginx_sqlmvp:first sqlmvp/nginx-sqlmvp:first

 

 

Syntax : docker push username/repository:tag

Ex) docker push sqlmvp/nginx-sqlmvp:first

 

 

 

 

 

[참고자료]

·         docker commit : https://docs.docker.com/engine/reference/commandline/commit/

·         docker pull : https://docs.docker.com/engine/reference/commandline/pull/

·         docker push : https://docs.docker.com/engine/reference/commandline/push/

 

 

 

2019-02-08 / Sungwook Kang / http://sqlmvp.kr

 

Docker, 이미지 생성, docker commit, docker push, docker tag, 도커 허브, 도커 커밋

Docker Container 리소스 제한

-         CPU, Memory, Disk I/O 리소스 사용량 설정

 

·         Version : Docker

 

컨테이너를 생성할 다양한 옵션으로 컨테이너 리소스 사용량을 조절할 있다. 아무런 옵션을 입력하지 않으면 기본적으로 호스트의 모든 리소스를 제한없이 사용할 있게 되어, 여러 컨테이너 실행 리소스 사용의 불균형이 발생할 수도 있다.

 

이번 포스트에서는 시스템 리소스(CPU, MEMORY, Disk I/O) 컨테이너 실행시 설정하거나 이미 운영중인 컨테이너에서 리소스를 수정하는 방법에 대해서 살펴 본다.

 

현재 컨테이너에 설정된 리소스를 확인하는 방법은 docker inspect 명령을 사용한다. docker inspect 많은 항목을 나타내는데 “HostConfig” 항목에서 리소스를 확인할 있다.

docker inspect nginx

 

 

[메모리 제한]

메모리는 m(Megabyte), g(Gigabyte) 단위로 설정 있으며 최소 메모리는 4MB이다. 컨테이너 내부에서 동작하는 프로세스가 컨테이너에 할당된 메모리를 초과하면 컨테이너는 자동으로 종료되므로 적절한 메모리를 설정해야한다. 아래 스크립트는 컨테이너 실행 메모리를 1 GB 제한한다.

docker run -d –name nginx1g --memory=1g nginx

 

컨테이너가 실행되었으면 해다 컨테이너의 메모리를 확인한다. docker inspect 많은 정보를 나타내므로 grep 명령어를 함께 사용하여 Memory 부분만 표시하였다.

docker inspect nginx1g | grep "Memory"

 

 

컨테이너의 swap메모리는 기본적으로 설정된 메모리의 2배로 설정되지만 별도로 설정할 있다. 아래 스크립트는 swap메모리를 4GB 설정한다.

docker run -d –name nginx1g --memory=1g --memory-swap=4g nginx

 

 

[CPU제한]

컨테이너 CPU 전체 CPU 사용량에서 리소스 할당을 설정한다. , 가상머신의 경우 특정 갯수의 CPU 할당 받지만 컨테이너의 경우 전체 사용량에서 얼마나 사용할지를 결정한다. 또한 CPU 사용하는 다양한 옵션이 있다.

·         --cpu-shares : 기본값은 1024 CPU 할당에서는 1 뜻한다. 2048 설정할 경우 기본 컨테이너보다 2 많은 시간을 할당 받을 있다.

docker run -d –name nginx --cpu-share=2048 nginx

 

·         --cpuset-cpus : 호스트에 여러개의 CPU 있을 컨테이너가 특정 CPU 사용하도록 설정한다. 아래 스크립트는 컨테이너가 3번째 CPU 사용하도록 설정한다.

#3번째 CPU 사용

docker run -d –name nginx --cpuset-cpus=2

 

#1, 4 번째 CPU 사용

docker run -d –name nginx --cpuset-cpus=”0,3”

 

#1,2,3번째 CPU 사용

docker run -d –name nginx --cpuset-cpus=”0-2”

 

 

·         --cpu-period, --cpu-quota : CPU 주기를 설정하며 -period 기본값은 100000이며 100ms 뜻한다, -quota -period 설정된 시간 CPU 스케줄링에 얼마나 할당할 것인지 설정한다. 예를 들어 -period = 100000이고 -quota=25000 할당하면 CPU주기가 ¼ 줄어 일반적인 컨테이너보다 CPU성능이 ¼ 감소한다. 컨테이너는 -period/-quota만큼 CPU 할당을 받는다.

docker run -d --name nginx --cpu-period=100000 --cpu-quota= 100000 nginx

 

·         --cpus : 이전의 --cpu-period, --cpu-quota, --cpu-share 비슷하지만 좀더 직관적으로 CPU사용량을 정의할 있다. 예를 들어 --cpus=0.1이라고 한다면 해당 컨테이너는 전체 CPU 중에 10% 사용한다는 뜻이다.

Docker run -d --name nginx --cpus=0.1 nginx

 

 

[I/O 제한]

컨테이너 생성시 아무런 제한을 하지 않으면 디스크I/O또한 모든 대역폭을 하나의 컨테이너가 사용할 있으므로 상황에 따라 I/O 제한 설정이 필요하다.  사용 형식은 [디바이스이름]:[] 이다.

·         --device-write-bps, --device-read-bps :  초당 읽기, 쓰기를 MB 단위로 설정하여 대역폭 제한한다. 아래 스크립트는 초당 쓰기를 10MB 제한한다.

docker run -it --name nginx --device-write-bps /var/data:10mb nginx

 

 

·         --device-write-iops, --device-read-iops : IO 대한 상대적인 값으로 아래 스크립트는 디스크에 대해 10IOPS 제한한다는 뜻이다.

docker run -it --name nginx --device-write-iops /var/data:10 nginx

 

 

[실행중인 컨테이너 리소스 재설정]

이미 실행중인 컨테이너의 리소스 설정을 변경할 때에는 docker update 명령을 사용한다. 아래 예제는 CPU 사용량을 10% 제한한다.

docker update [리소스 설정] [컨테이너이름]

docker update --cpus=0.1 nginx

 

 

[참고자료]

·         docker run : https://docs.docker.com/engine/reference/commandline/run/

 

 

 

2019-02-06 / Sungwook Kang / http://sqlmvp.kr

 

Docker, 컨테이너 리소스 제한, 도커 자원 할당, 컨테이너 설정, 컨테이너 CPU, 컨테이너 메모리, 컨테이너 I/O

Docker Container 로그 확인

-         컨테이너에서 발생하는 다양한 로그 확인

 

·         Version : Docker

 

어떠한 시스템을 운영하던지 로그는 매우 중요하다. 로그는 현재 서비스의 다양한 상태를 확인할 있는 훌륭한 도구이기 때문이다. Docker 경우 다양한 방법으로 컨테이너 로그를 남기는데, 이번 포스트에서는 컨테이너의 표준 입력(STDIN),  표준 출력(STDOUT), 표준 오류(STDERR) 로그를 별도의 메타데이터 파일로 저장하며 이를 확인하는 방법에 대해서 살펴본다.

 

컨테이너의 로그를 확인하는 명령은 docker logs 사용한다. docker logs 명령은 컨테이너의 표준 출력을 표시함으로써 애플리케이션 상태를 있다.

docker log [container name]

docker logs mariadb

 

 

컨테이너의 로그가 너무 많아 읽기 힘들면 --tail 옵션을 사용하여 마지막 로그부터 사용자가 지정한 라인까지 출력하도록 있다. 아래 예시는 마지막 로그의 10줄만 표시한다.

docker logs --tail 10 mariadb 

 

 

--since 옵션은 입력 받은 유닉스 시간 이후의 로그를 확인할 있으며 -t옵션으로 타임 스탬프를 표시할 수도 있다.

Docker logs --since 1549150300 -t mariadb

 

 

-f 옵션을 사용하면 실시간으로 생성되는 로그를 스트림으로 확인할 있다.

 


로깅 드라이버는 기본적으로 json-file 설정되지만 도커 데몬 시작 옵션에서 --log-driver 옵션을 사용하여 기본적으로 사용할 로깅 드라이버를 변경할 있다. 아래 스크립트는 nonoe 로깅드라이버로 alpine 컨테이너를 시작한다.

docker run -it --log-driver none alpine ash

 

실행중인 컨테이너의 로깅 드라이버를 확인하려면 docker inspect 명령을 실행한다.

docker inspect -f '{{.HostConfig.LogConfig.Type}}' <CONTAINER>

docker inspect -f '{{.HostConfig.LogConfig.Type}}' mariadb

 

 

현재 로깅 드라이버는 매우 다양하게 지원되고 있으며 아래 링크에서 지원되는 드라이버를 확인할 있다.

·         Configure logging drivers  : https://docs.docker.com/config/containers/logging/configure/

 

docker logs 명령은 json-file journald이외의 드리이버에서는 사용할 없다.

 

 

[참고자료]

·         View logs for a container or service  : https://docs.docker.com/config/containers/logging/

·         Configure logging drivers  : https://docs.docker.com/config/containers/logging/configure/

 

 

2019-02-03 / Sungwook Kang / http://sqlmvp.kr

 

Docker, docker logs, 컨테이너 로그

Docker Volume (도커 볼륨)

-         도커 볼륨을 이용해서 데이터 공유하기

 

·         Version : Docker

 

Docker 컨테이너가 삭제(또는 재시작)되면 컨테이너의 변경된 데이터가 함께 삭제된다.  데이터를 영속적으로 보존하기위해 volume  옵션을 사용하여 호스트 저장소를 마운트하여 사용한다.

·         Docker Volume (호스트 볼륨 공유) : http://sqlmvp.kr/221449590567

·         Docker Volume (컨테이너 볼륨 공유) : http://sqlmvp.kr/221451346970

 

이번 포스트에서는 도커 자체에서 제공하는 볼륨 기능을 활용하는 방법에 대해서 알아본다. 볼륨을 생성할 플러그인을 사용하여 다양한 종류의 스토리지 백엔드를 있지만 이번 포스트에서는 기본적인 도커 엔진에서 제공되는 local 사용한다.

 

 도커 볼륨을 생성하는 명령어는docker volume create 사용한다. 생성된 볼륨을 확인하는 방법은 docker volume ls 이다.

docker volume create –name my-vol

docker volume ls

 


 

도커 볼륨은 실제 호스트의 어느 경로에 만들어 졌는지 확인하는 방법은 docker volume inspect 명령을 사용한다.

docker volume inspect my-vol

 

 

도커 볼륨을 삭제하는 명령어는docker volume rm 이다. 참고로 컨테이너를 삭제해도 볼륨은 자동으로 삭제되지 않는다.

docker volume rm my-vol

 

사용되지 않는 모든 볼륨을 삭제하려면 아래 명령을 실행 한다.

docker volume prune

 

도커 볼륨을 사용하는 컨테이너를 생성하기 위해서는 [볼륨이름]:[컨테이너 공유 디렉터리]  순으로 명령을 입력한다. 아래 예시는 my-vol이라는 볼륨을 컨테이너의 /app 디렉터리에 마운트 한다. /app 디렉터리에 파일을 쓰면 해당 파일이 볼륨에 저장된다.

docker run -d --name devtest -v my-vol:/app nginx:latest

 

도커 볼륨은 여러 컨테이너에서 사용할 있으므로 아래 그림처럼 파일을 쉐어하여 머신간에 데이터를 공유할 있다.

 


만약 여러 컨테이너가 있고 여러