이쿠의 슬기로운 개발생활

함께 성장하기 위한 보안 개발자 EverNote 내용 공유

클라우드/Kubernetes

01. Kubernetes 이론

이쿠우우 2020. 8. 5. 21:50
반응형

Kubernetes 란?

선행 학습으로 컨테이너 런타임 Tool에 대한 지식이 필요함 [예 : Docker, CRI-O, RKT 등등] 

컨테이너를 쉽고 빠르게 배포/확장하고 관리를 자동화해주는 오픈소스 플랫폼

구글의 컨테이너 내부 배포시스템 borg를 기반으로 2014년에 프로젝트를 시작

너무 길어서 K8s = 케이츠라고도 불림

전 세계적 스케일의 경험과 기술이 반영되어 있음

단순한 컨테이너 플랫폼이 아닌 마이크로서비스, 클라우드 플랫폼을 지향

컨테이너 오케스트레이션( Orchestration) 의 대표주자

컨테이너 오케스트레이션 ( Orchestration) 이란?

여러 개의 서버에 컨테이너를 배포하고 운영하면서 서비스 디스커버리 같은 기능을 이용하여 서비스 간 연결을 쉽게 해주는 것

예)

서버마다 app01, db01, cache01 같은 이름을 지어주고 하나하나 접속하여 관리하는 것이 아니라

server1, 2, 3, 4.. 를 하나로 묶어 적당한 서버를 자동으로 선택해 애플리케이션을 배포하고

부하가 생기면 컨테이너를 늘리고 일부 서버에 장애가 발생하면

정상 동작 중인 서버에 다시 띄워 장애를 방지

Container Server가 여러 대가 있다면 관리하기가 힘드니 


Container Orchestration을 사용해서 편리하게 관리함

 

 


 

 

Kubernetes Desired State

 

Kubernetes의 핵심은 계속해서 원하는 상태를 만들기 위해서 현재 상태를 바꾸는 플랫폼

 

 


 

Kubernetes 사용 예시

micro-service archtechture 라면

어떤 컨테이너는 유저 Upload만 다루고

어떤 컨테이너는 인증만 다루고, 어떤 건 결제만 다루고 하는데

이 모든 컨테이너들은 동시에 업로드가 되어야 함

배포할 때는 문제가 되지 않지만

많은 컨테이너를 관리하다 보면 분명히 문제가 발생할 수 있음

예를 들어 하나의 컨테이너가 죽으면 서비스의 핵심 파트일 수 있으니 빠르게 재시작을 해야 함

사람이 관리하다 보면 24시간 지켜볼 수 없으니 문제가 발생할 수밖에 없음

이때 Kubernetes를 사용하면 문제가 깔끔하게 해결됨

Kubernetes는 많은 컨테이너들을 관리하며 죽으면 알아서 살려내고

Update가 있으면 서비스가 멈추지 않고 Update가 되게 해주는 등 컨테이너 관리를 굉장히 편하게 해 줌

 


 

Kubernetes 제공 기능

1. 서비스 디스커버리와 로드 밸런싱

쿠버네티스는 DNS 이름을 사용하거나 자체 IP 주소를 사용하여 컨테이너를 노출할 수 있음

즉 서로 다른 서비스를 쉽게 찾고 통신할 수 있음

컨테이너에 대한 트래픽이 많으면, 쿠버네티스는 네트워크 트래픽을 로드밸런싱 하고 배포하여 배포가 안정적으로 이루어질 수 있음

서비스 디스커버리란?
네트워크 상의 장치와 서비스를 자동으로 탐지하는 것
클라우드 환경이 되면서 서비스가 오토 스케일링 등에 의해서 동적으로 생성되거나
컨테이너 기반의 배포로 인해서, 서비스의 IP가 동적으로 변경되는 일이 잦아짐
그래서 서비스 클라이언트가 서비스를 호출할 때 서비스의 위치 (즉 IP주소와 포트)를 알아낼 수 있는 기능이 필요한데,
이것을 바로 서비스 디스커버리 (Service discovery)라고 함
로드 밸런싱이란?
하나의 인터넷 서비스가 발생하는 트래픽이 많을 때
여러 대의 서버가 분산 처리하여 서버의 로드율 증가, 부하량, 속도 저하 등을 고려하여
적절히 분산 처리하여 해결해주는 서비스.

2. 스토리지 오케스트레이션

  • 쿠버네티스를 사용하면 로컬 저장소, 공용 클라우드 공급자 등과 같이 원하는 저장소 시스템을 자동으로 탑재할 수 있음

3. 자동화된 롤아웃과 롤백

  • 쿠버네티스를 사용하여 배포된 컨테이너의 원하는 상태를 서술할 수 있으며 현재 상태를 원하는 상태로 설정한 속도에 따라 변경할 수 있음
  • 예를 들어 쿠버네티스를 자동화해서 배포용 새 컨테이너를 만들고, 기존 컨테이너를 제거하고, 모든 리소스를 새 컨테이너에 적용할 수 있음

4. 자동화된 빈 패킹(bin packing)

  • 컨테이너화 된 작업을 실행하는 데 사용할 수 있는 쿠버네티스 클러스터 worker node를 제공
  • 각 컨테이너가 필요로 하는 CPU와 메모리(RAM)를 쿠버네티스에게 지시
  • 쿠버네티스는 컨테이너를 worker node에 맞추어서 리소스를 가장 잘 사용할 수 있도록 해줌

5. 자동화된 복구(self-healing)

  • 쿠버네티스는 실패한 컨테이너를 다시 시작하고,
  • 컨테이너를 교체하며,
  • ‘사용자 정의 상태 검사’에 응답하지 않는 컨테이너를 죽이고,
  • 서비스 준비가 끝날 때까지 그러한 과정을 클라이언트에 보여주지 않음

6. 시크릿과 구성 관리

  • 쿠버네티스를 사용하면 암호, OAuth 토큰 및 SSH 키와 같은 중요한 정보를 저장하고 관리할 수 있음
  • 컨테이너 이미지를 재구성하지 않고 스택 구성에 비밀을 노출하지 않고도 비밀 및 애플리케이션 구성을 배포 및 업데이트 가능

7. 다양한 배포 방식 지원

  • Deployment control
    • 새로운 버전의 애플리케이션을 다양한 전략으로 무중단 배포 가능
  • Statefulsets control
    • 실행 순서를 보장하고 호스트 이름과 볼륨을 일정하고 사용할 수 있어서 데이터가 중요한 경우에 사용
  • DaemonSet control
    • 로그나 모니터링이 모든 worker node에 설치가 필요한 경우 사용
  • Job, CronJob control
    • 배치성 작업에 사용

 

 

 


 

 

Kubernetes Component

Kubernetes를 배포하면 Cluster를 얻음

Kubernetes의 전체적인 Cluster를 그림으로 표현해봄

Cluster 

Kubernetes에서 관리하는 컨테이너화 된 애플리케이션을 실행하는 노드라고 하는 기계의 집합

클러스터는 최소 1개의 Worker node와

최소 개의 Master Node를 가짐


 

Master Node 

Master Node는 Master, Master component, Master Node, Control Plane component, Control Node

다양하게 불려짐

이 글에서는 Master Node라고 명시하겠음

 

Master Node는 클러스터에 관한 전반적인 결정을 수행하며 클러스터를 이벤트를 감지하고 반응함

모든 명령은 마스터의 API 서버(그림 : kube-api-server)를 호출하여 Worker node와 통신함

Master Node는 다양한 모듈이 확장성을 고려하여 기능별로 나누어져 있음

Master Node가 죽으면 클러스터를 관리할 수 없기 때문에 보통 3대 이상의 홀수로 구성하여 안정성을 높임

소규모 환경에서는 Master Node를 분리하지 않고 같은 서버에 구성하기도 함

 

참고) Master Node를 여러 대 구성할 때 haproxy를 사용하기도 함

 

 

 

kube API Server

API 서버는 모든 요청을 처리하는 Master Node의 핵심 모듈.

kubectl의 요청뿐만 아니라 내부 모듈의 요청도 처리하며 권한을 체크하며 요청을 거부할 수 있음

Worker node에서 실행 중인 컨테이너의 로그를 보여주고 명령을 보내는 등 디버거 역할도 수행함

실제로 하는 일은 원하는 상태를 key-value 저장소에 저장하고 저장된 상태를 조회하는 단순한 작업을 수행

API 서버는 요청을 받으면 etcd 저장소와 통신할 뿐 실제로 상태를 바꾸는 건 scheduler와 controller임

Kubectl
kube API server와 통신하기 위한 Client 도구

 

 

 

 

etcd

분산 데이터 저장소

Key-value 저장소

여러 개로 분산하여 복제할 수 있어서 안정성이 높고 빠름

단순이 값을 저장하고 읽는 기능뿐만 아니라 watch기능도 있어서 상태가 변경되면 바로 체크하여 로직 실행 가능

클러스터의 모든 설정, 상태 데이터가 이곳에 저장됨

나머지 모듈은 stateless 하게 동작하기 때문에 etcd만 잘 백업해놓으면 언제든지 kubernetes Cluster를 복구할 수 있음

etcd는 오직 API 서버와만 통신하고 다른 모듈은 API 서버를 거쳐서 etcd 데이터에 접근해야 함

 

참고)

  • k3s와 같은 초경량 kubernetes 배포판에서는 etcd 대신 sqlite를 사용하기도 함

 

 

 

 

 

kube Scheduler

Pod, Service 등 각 리소스들을 적절한 Worker node에 할당하는 역할을 수행

 

 

 

 

 

kube Controller Manager

kubernetes에 있는 거의 모든 오브젝트의 상태를 관리

아래서 설명할 kubernetes controller에 해당하는 모듈로

Replica, Service, Volume, Deployment 등을 생성하고 이를 각 Worker node에 배포하며 관리하는 역할을 수행

오브젝트별로 철저하게 분업화되어

Deployment는 ReplicaSet을 생성하고

ReplicaSet은 pod를 생성하고

Pod은 스케줄러가 관리하는 방식임

 

 

 

 

 

Cloud Controller Manager

Cloud Controller는 AWS, GCE, Azure 등 클라우드에 특화된 모듈

worker Node를 추가, 삭제하고 LoadBalancer를 연결하거나 볼륨을 붙일 수 있음

각 Cloud 업체에서 인터페이스에 맞춰 구현하면 되기 때문에 확장성이 좋고 많은 곳에서 자체 모듈을 만들어서 제공하고 있음

 


Worker Node 

Woker, component, Node, component, Worker Node 등 다양하게 불려짐

이 글에서는 Worker Node 라고 명시하겠음

 

Worker Node는 동작중인 파드를 유지시키고 Master Node가 전달해주는 작업을 Pod에 반영하는 역할을 수행함

 

 

 

 

kubelet (큐블릿)

kubelet을 통해 다양한 컨테이너를 관리함

worker Node에 할당된 Pod의 생명주기를 관리

Pod를 생성하고 Pod안의 컨테이너에 이상이 없는지를 확인

주기적으로 Master Node에 Pod의 상태를 전달함

API 서버의 요청을 받아 컨테이너의 로그를 전달하거나 특정 명령을 대신 수행하기도 함

 

 

kube Proxy

큐블릿이 Pod를 관리한다면 프록시는 Pod로 연결되는 네트워크를 관리함

Worker node로 들어오는 네트워크 트래픽을 적절한 컨테이너로 라우팅함

TCP, UDP, SCTP 스트림을 포워딩하고 여러 개의 Pod를 라운드로빈 형태로 묶어서 서비스를 제공할 수 있음

라운드로빈이란?
스케줄링의 한 방법
하나의 자원을 독점해서 작업이 완료될 때까지 차지하는 것이 아니라
자원을 조금씩 돌아가면서 할당받아 실행되는 방식

 

 

 

Pod

Pod를 통해서 배포된 컨테이너를 실행함

kubernetes는 CRI(Container runtime interface)를 구현한 다양한 컨테이너 런타임을 지원

컨테이너 런타임은 보통 Docker를 생각하기 쉬운데 Docker 이외에 다양한 컨테이너 런타임을 지원

 

컨테이너 런타임 종류

  • Docker
  • rkt
  • CRI-O
  • Hyper container

 

 


 

 

Kubernetes Object

 

아래의 그림은 Kubernetes Object 중 Kubernetes를 이해하는데 가장 기본적이고 중요한

Pod, Service, Volume, NameSpace 4가지 Object의 전체적인 관계 흐름을 표현해봤음

 

kubernetes Object란?

kubernetes가 상태를 관리하기 위한 대상을 Object라고 부름

하나의 의도를 담은 레코드,

Object는 kubernetes에서 영속성을 가지는 개체임

오브젝트를 동작시키기 위해서는 kube-api-server를 이용해야 함

Container를 편리하게 관리하기 위한 다양한 Object를 제공하고 있으며

새로운 Object를 추가하기가 매우 쉽기 때문에 확장성이 좋음

 

대표적인 Object = Pod, Service, Volume, Namespace 

 

Object는 kubernetes의 클러스터 상태를 나타냄

  1. 어떤 컨테이너화 된 애플리케이션이 동작중인지, 어느 노드에서 동작중인지
  2. 그 애플리케이션이 이용할 수 있는 리소스
  3. 그 애플리케이션이 어떻게 재구동 정책, 업그레이드가 동작하고 있는지

 

각각의 Object는 Spec과 Status라는 필드를 갖게 됨

Spec

kubernetes는 Object의 Spec을 통해 사용자가 기대하는 상태(Desired State)가 무엇인지 알 수 있음

즉 Spec은 해당 Object가 어떤 상태를 가질지에 대한 명세를 가지고 있는 것

Spec (명세)는 YAML 파일 or JSON 파일로 정의하고 이를 manifest(매니페스트)라고 부름.

  • 참고) : 보통 YAML 파일을 더 많이 사용함

정의된 파일에 오브젝트 종류와 원하는 상태를 입력하여 관리

예)

Status

기대되는 값에 대비한 현재의 상태를 Object의 Status를 통해 알 수 있음

Status는 실제로 클러스터에 떠 있는 Ojbect가 어떤 상태를 가지고 있는지에 대한 정보를 담고 있는데

이것은 Kubernetes System에 의해서 바뀜

[ 참고 명령어 ] 

kubectl get all

kubectl describe pod 

 

이 글에서는 많은 오브젝트 중 가장 기본이 되고 중요한 오브젝트를 설명하겠음

참고)

  • 아래 설명하는 것 이외에도 다양한 object가 존재함

 


 

Pod

kubernetes 에서 배포할 수 있은 가장 작은 단위이자 기본 단위

Pod는 클러스터(Cluster)에서의 Running 프로세스를 뜻함

한 개 이상의 Container와 Storage, Network 속성을 가짐

 

Pod 특징 1. Pod에 속한 Container는 Network를 공유하고 서로 localhost로 접근 가능

Pod 내의 컨테이너는 IP와 Port를 공유함

예)

Docker에서의 Container 간의 통신

 =   Container A의 IP주소 : 8080 <->Container B의 IP주소 : 3306

Pod 안에서 컨테이너 간의 통신

 =  Pod의 IP주소 or localhost : 8080 <->Pod의 IP주소 or localhost : 3306

 

Pod 특징 2. Pod에 속한 Container는 Storage(volume)를 공유

Pod 안에 속한 다른 Container의 파일을 읽어올 수 있음

yaml spec에 volume을 명시해야 생성됨

emptyDir : Pod가 생성될 때 생성되고 Pods가 삭제될 때 같이 삭제되는 임시 volume

 

Pod 특징 3. Container를 하나만 사용하는 경우도 반드시 Pod로 감싸서 관리함

즉 kuberentes의 특징 중 하나로 Container를 개별적으로 하나씩 배포하는 것이 아니라
Pod 단위로 배포함

 


 

Volume

저장소와 관련된 오브젝트

컨테이너는 기본적으로 상태가 없는(Stateless) 앱을 사용함

Stateless란?
어떤 이유로 컨테이너가 죽었을 때 현재까지의 데이터가 사라진다는 것

앱의 특성에 따라서 컨테이너가 죽더라도 데이터가 사라지면 안 되고 보존되어야 하는 경우가 있음

예) mysql 같은 데이터베이스도 컨테이너가 내려가거나 재시작했다고 해서 데이터가 사라지면 안 됨

 

그때 사용할 수 있는 게 Volume.

볼륨을 사용하게 되면 컨테이너가 재시작을 하더라도 데이터가 사라지지 않고 유지됨

 

Volume 은 Pod내의 컨테이너 간의 공유가 가능함

호스트 디렉터리를 그대로 사용할 수도 있고

Amazon Elastic Block Store (EBS) 같은 스토리지를 동적으로 생성하여 사용할 수 도 있음

컨테이너의 외장 디스크 역할을 함

Pod가 기동 할 때 디폴트로, 컨테이너마다 로컬 디스크를 생성해서 기동 되는데,
이 로컬 디스크의 경우에는 영구적이지 못함
즉 컨테이너가 리스타트되거나 새로 배포될 때마다 로컬 디스크는 Pod 설정에 따라서 새롭게 정의돼서 배포되기 때문에,
디스크에 기록된 내용이 유실됨
데이터 베이스와 같이 영구적으로 파일을 저장해야 하는 경우에는
컨테이너 리스타트에 상관없이 파일을 영속적으로 저장해야 하는데,
이러한 형태의 Storage를 Volume이라고 함

 

Volume의 종류

emptyDir :

Pod가 생성될 때 생성되고 Pods가 삭제될 때 같이 삭제되는 임시 volume

Pod 내부 container 간 공유 가능

 

hostPath :

노드 로컬 디스크의 경로를 Pod에 마운트에서 사용하는 volume

여러 Pod 사이에서 공유 가능

 

등등등 다양한 volume 종류가 있음 추후 kubernetes Volume 글에서 자세히 설명하겠음

 

 

 


 

 

 

Service

네트워크와 관련된 오브젝트

Pod을 외부 네트워크와 연결해주고 여러 개의 Pod을 바라보는 내부 로드 밸런서를 생성할 때 사용

쿠버네티스 클러스터 안에 컨트롤러를 이용해서 Pod를 띄웠다면 이제 그 Pod들에 접근하는 방법에 대해 알아봐야 함

Pod는 컨트롤러에 의해 관리되기 때문에 한 군데에 고정돼서 떠 있지 않고 클러스터를 옮겨 다니게 됨

이 과정에서 노드를 옮기면서 실행되기도 하고 클러스터 내의 Pod IP가 변경되기도 함

이렇게 동적으로 변하는 Pod들에 고정된 방법으로 접근하기 위해서 사용하게는 쿠버네티스의 서비스(Service) 임

서비스를 사용하게 되면 Pod가 클러스터내의 어디에 있는지에 상관없이 고정된 주소를 이용해서 접근이 가능

Service에서는 대표적으로 4가지 종류가 있음 : ClusterIP, NodePort, LoadBalancer, ExternalName

 

 

ClusterIP

default service type

내부에 노출하는 IP

클러스터 내부의 노드나 포드에서 이 ClusterIP를 이용해서 서비스에 연결된 포드에 접속 가능

클러스터 외부에서는 접속 불가능

즉 프론트앤드가 백앤드와 통신할 때 주로 사용됨

 

 

 

 

NodePort

 

외부에서 접속하기 위해 사용

각 Worker Node에 지정된 포트를 할당하는 방식

Cluster 외부에서 내부의 포드로 접근할 때 사용할 수 있는 가장 간단한 방법

NodePort 서비스가 라우팅 되는 ClusterIP 서비스가 자동으로 생성

<Node IP>:<Node Port>를 요청하여, 클러스터 외부(각 Node의 IP대역대와 같은 망)에서

NodePort 서비스에 접속 가능

port 번호 = 30000 ~ 32767 사이의 값을 사용해야 함

 

모든 Node IP에서 접근이 가능

Master Node IP로만 접근이 가능한 것이 아니라, 모든 Worker Node의 IP와 포트를 통해서도 접근이 가능

즉 pod이 1번 Worker Node에 떠있다고 하더라도 2번 Worker Node or Master Node의 ip로 접근 가능

 

 

 

LoadBalancer

AWS, GCP 같은 클라우드 서비스를 사용할 때 사용 가능한 옵션

포드를 클라우드에서 제공해주는 로드밸런서와 연결해서

그 로드밸런서의 External IP를 이용해서 클러스터 외부에서 접근이 가능하게 해 줌

외부 로드 밸런서가 라우팅 되는 NodePort와 ClusterIP 서비스가 자동으로 생성

주의
LoadBalancer로 노출하고자 하는 각 Service Object 마다 자체의 Externel IP 주소를 갖게 됨
즉 Service Object 가 3개면 LoadBalancer 도 3개가 돼야 각각 Service에 접근할 수 있음
Service Object 가 많을 경우 그만큼의 Externel IP가 생성되니
클라우드 플랫폼 이용 시 과금이 발생할 수 있으니 주의해야 함

Public Cloud LoadBalancer

  • AWS, Azure, GCP 사용 시 External IP가 자동으로 할당됨

On-Premise LoadBalancer

  • private 환경일 시 External IP 할당하는 방법으로는 MetalLB 등 Kubernetes Addon을 사용해야 함

 

 

 

ExternalName

서비스를 externalName의 값이랑 매치

클러스터 내부에서 외부로 접근할 때 주로 사용

이 서비스로 접근하면 설정해둔 CNAME값으로 연결돼서 클러스터 외부로 접근할 수 있음

외부로 접근할 때 사용하는 값이기 때문에 설정할 때 셀렉터가 필요 없음

 

 

 

 

Kubernetes Ingress

 

Service object의 type 은 아님 Kubernetes Addon 중 하나

Kubernetes의 ingress는 외부에서 쿠버네티스 클러스터 내부로 들어오는 네트워크 요청

클러스터의 진입점 역할을 수행

동일한 IP 주소로 여러 서비스를 노출시킬 수 있기 때문에 라우팅 규칙을 단일 리소스로 통합할 수 있음

즉, Ingress 트래픽을 어떻게 처리할지 정의함

쉽게 말하자면, Ingress는 외부에서 쿠버네티스에서 실행 중인

Deployment와 Service에 접근하기 위한, 일종의 관문 (Gateway) 같은 역할을 담당

하나의 클러스터에 여러 개의 ingress 설정 가능

nginx와 굉장히 유사함

 

 

Ingress 언어의 뜻
네트워크 트래픽은 ingress와 egress로 구분됨
Ingress는 외부로부터 서버 내부로 유입되는 네트워크 트래픽
engress는 서버 내부에서 외부로 나가는 트래픽

 


 

 

Namespace

 

kubernetes 클러스터 내의 논리적인 분리 단위

Pod, Service 등은 Namespace 별로 생성이나 관리가 될 수 있음

Namespace는 물리적으로 환경을 분리한 것이 아니기 때문에

다른 Namespace 간의 pod 라도 Service Object를 통해 통신 가능

 

예)

하나의 클러스터 내에, 개발/운영/테스트 환경이 있을 때,

클러스터를 개발/운영/테스트 3개의 네임 스페이스로 나눠서 운영할 수 있음

 

Pod에서 생성되는 Pause Container 역할

추후에 pod 네트워크 부분에서 자세히 설명하겠지만 

간단하게 설명하시면 Pod 안에는 사용자가 생성하지 않은 Pause라는 Container가 생성되어있는데

이 Pause Container를 통해 서로 다른 namespace에 있는 Pod 간에서도 자원과 네트워크를 공유할 수 있음

앞에서 Pod 내부의 컨테이너들은 네트워크와 볼륨을 공유하고 서로 localhost로 통신할 수 있다고 했음

좀 더 자세히 들어가면 Pod이 실행될 때 pause라는 이름의 컨테이너가 먼저 실행되고

이 pause컨테이너의 namespace를 Pod내부의 모든 컨테이너들이 공유해서 사용하게 됨

 

NameSpace 역할 예시 설명

다음과 같이 여러 NameSpace 안에는 Pod 가 구성이 된 상태에서 

각 Pod는 필요한 자원을 Kubernetes Cluster자원을 공유해서 사용을 하는데

한 Pod 가 자원을 모두 사용해버리면 나머지 Pod는 자원이 부족해지는 현상이 발생할 수 있음

이때 NameSpace를 사용하면 각 NameSpace에 미리 최대 자원을 지정해놔서 자원이 부족해지는 현상을 막을 수 있음

 

NameSpace 자원 지정 참고 기능 Object 종류

  • ResourceQuota
  • LimitRange

 

 

 

 

 


 

 

 

Kubernetes Controller

Kubernetes의 기본 Object로 애플리케이션을 설정하고 배포하는 것이 가능한데

이를 더 편리하게 관리해주는 것으로 Controller라는 개념이 있음

상위의 kubernetes object에서 object는 spec과 status를 가진다고 했는데

Object의 Status를 갱신하고

Ojbetct를 Spec에 정의된 상태로 지속적으로 변화시키는 것이 

Kubernetes Controller 임

즉 kubernetes controller는 기본적으로 유저가 '원하는' 상태를 읽어서

현재 상태와 비교해 '원하는' 상태로 클러스터의 싱크를 맞춰주는 역할을 함

Controller는 크게 4가지의 기능을 제공


 

1. Rolling Update

 

기존의 경우 Software Update 작업이 있을 시

서버를 내린 후 Update를 하고 다시 올리는 작업이 필요해서

주로 새벽에 작업하는 매우 큰 리스크가 있는 작업이었는데

Kubernetes Contorller를 사용할 시 다수의 Pod 도 무중단으로 쉽게 Update 할 수 있음

앱의 버전이 변경되어 새로운 버전의 배포가 필요할 때 사용할 수 있는 기능

 

방식 예) 복재 Pod 이 2개 있을 경우

1. 새 버전의 Pod 1개를 실행

2. 기존의 구 버전 pod 1개를 종료

3. 새 버전 Pod 2개를 실행

4. 마지막 구 버전 pod 2개를 종료


 

2. Auto Healing

 

Worker Node에서 동작 중이던 Pod 가 에러가 발생할 경우

또는

Worker Node 자체에 오류가 발생하면

Controller는 지속적으로 모니터링하다가 오류를 인식하고

자동으로 Pod를 다른 Worker Node로 새로 생성하며 문제를 해결


 

3. Auto Scaling

Pod의 리소스가 limited 상태가 되었을 때

Controller는 이 상태를 인지하고 Pod를 더 만들어 주어 부하를 줄여주어

안정적인 상태를 유지

 


 

4. Job

일시적으로 기능을 추가하거나 Test을 해야 하는 경우처럼

일시적인 작업을 해야 할 경우

그림과 같이 컨트롤러가 필요한 순간에만 Pod를 만들어 해당 작업을 수행하고 삭제함

이렇게 되면 그 순간에만 자원이 사용되고 이후에 자원이 다시 반환되기 때문에

효율적인 자원 활용이 가능

 


 

Kubernetes Controller 종류 설명

yaml 매니페스트 형식 중 Kind에 해당하는 옵션에 해당함.

여기서는 많은 Controller 중 가장 기본이 되고 많이 사용하는 Controller를 설명하겠음

참고 : 아래 설명하는 것 이외에도 다양한 Controller가 존재함

 

Replication Controller

kubernetes의 가장 기본적인 컨트롤러

하지만 ReplicaSet 등장으로 곧 사라지게 될 컨트롤러 이기도 함

Pod을 여러 개 복제하고, 사용자가 기대하는 상태로 Pod의 개수/상태를 유지하는 역할을 수행

보통 명시된 동일 Pod 개수에 대한 가용성을 보증하는 데 사용

컨트롤러를 사용하지 않고 Pod를 직접 띄웠을 경우

Pod에 이상이 생겨서 종료되거나 삭제됐을 때 문제가 발생하고 재시작 또한 어려움

Replication Controller는 지정된 숫자만큼 Pod가 항상 실행되고 있도록 관리하는 역할을 수행하여

상위 문제에 대응할 수 있음

 

Pod 2개를 명시해둔 Replication Conroller가 있다면?

ex) spec : replicas : 2

장애나 다른 이유로 컨트롤러 개수가 2개보다 작아졌을 때 = 다시 새로운 Pod를 띄워서 Pod 개수를 2개로 조정

Pod가 2개보다 많아졌을 때 =  Pod를 줄여서 2개만큼만 실행되게 조정

 

Rolling Update 사용 가능

명령어 예)

kubectl rolling-update nginx --image=nginx:1.13.12

 


 

ReplicaSet

ReplicaSet is the next-generation Replication Controller

ReplicaSet은 Replication Controller의 새로운 버전.

ReplicaSet은 Replication Contoller와 거의 동일하게 동작함

ReplicaSet은 복제할 개수, 개수를 체크할 라벨 선택자, 생성할 Pod의 설정값(템플릿)등을 가지고 있음

즉 ReplicaSet의 목적은 레플리카 Pod 집합의 실행을 항상 안정적으로 유지하는 것

참고 : 직접적으로 ReplicaSet을 사용하기보다는 Deployment 등 다른 오브젝트에 의해서 사용되는 경우가 많음

Replication Controller와 ReplicaSet 차이점

1. Labels Selector 차이

 

ReplicaSet : 집합 기반(set-based) Selector 지원

- 일치성 기준 요건

- in, notin, exists 연산자 지원

 

Replication Controller  : 등호 기반(equal-based) Selector 지원

- 집합성 기준 요건

- =, ==, != 지원

 

Labels Selector 란?

Label 

 - Pod와 같은 오브젝트에 첨부된 키와 값의 쌍으로 오브젝트의 특성을 식별하는 데 사용,  고유하지 않음

Label Selector

 - 많은 오브젝트가 같은 레이블을 가질 텐데 이 레이블을 구분할 수 있도록 하는 연산자.

 - 일치성 기준 요건, 집합성 기준 요건 두 종류의 Selector를 지원함

 

 

2. ReplicaSet 은 Rolling-Update를 지원하지 않음

Replication Controller는 Rolling Update를 지원하지만

ReplicaSet에서 Rolling Updat e를 사용하기 위해서는

Deployments를 사용해야 함 (아래에서 설명)

 


 

Deployment

Deployment는 kubernetes에서 일반적으로

상태가 없는 앱(stateless app)을 배포할 때 사용하는 가장 기본적인 컨트롤러임

 

stateless app 이란?
한 Session에서 생성된 client데이터를  
해당 클라이언트와의 다음 Session에서 사용하기 위해 저장하지 않는 프로그램
각각의 session은 처음 Session인 것처럼 수행되며 응답은 이전 Session의 데이터에 종속되지 않음
server는 client에 대한 상태를 저장하지 않음
대신 세션 데이터는 client에 저장되고 필요에 따라 서버로 전달 됨

kubernetes 초반에는 Replication Controller가 담당했지만

현재는 Deployment가 가장 기본적인 배포 방법으로 사용되고 있음

Deployment는 Pod와 ReplicaSet에 대한 선언적 업데이트를 제공함

즉 Deployment 도 Replicaset을 사용함, ReplicaSet의 상위 버전이라고 생각하면 됨

보통 Deployment 가 생성되면 해당 Deployment에 대응하는 레플리카셋도 함께 생성됨

따라서 Deployment를 사용하면 Pod와 레플리카셋을 직접 생성할 필요가 없음

 

Deployment 기능

1. 버전 관리 가능이 추가됨

이미지 태그가 바뀌면 기록함

 

2. Deployment는 ReplicaSet을 세밀하게 관리할 수 있음

앱의 배포를 보다 세밀하게 관리할 수 있음

배포에 대한 기능이 세분화되어 있음

 

3. 실행시켜야 할 Pod의 개수를 유지

 

4. 배포할 때 롤링 업데이트가 가능

 

5. 배포 도중 멈췄다가 다시 배포 가능

 

6. 배포 후 이전 버전으로 롤백 가능

 

 

Deployment yaml 파일 설정 설명

apiVersion: apps/v1            # 사용하고 있는 쿠버네티스 API 버전이 어떤 것인지 (Deployment를 사용할 수 있는 apps/v1으로 설정)

kind: Deployment               # 어떤 종류의 Object를 생성하고자 하는지 설정 (Deployment로 설정) 

metadata:                      # 이름 문자열, UID, 선택적인 네임스페이스 를 포함하여 오브젝트를 유일하게 구분지어 줄 데이터 

  name: nginx-deployment       # 클러스터의 각 오브젝트가 가지는 고유한 이름, 동일한 네임스페이스 내에서 하나만 가질 수 있음

  labels:                      # 오브젝트에 첨부된 키와 값의 쌍으로 오브젝트의 특성을 식별하는데 사용, 고유하지 않음

    app: nginx                 # labels 는 여러 값을 가질 수 있음

spec:                          # 오브젝트에 대해 어떤 상태를 의도하는지 설정 (즉 deployment 설정)  

  replicas: 3                  # Pods를 몇개 띄울것인지 설정, template에 매칭되는 Pods 3개를 구동하는 deployment 임

  selector:                    # 많은 오브젝트가 같은 레이블을 가질때 label을 구분할 수 있도록 하는 연산자(일치성기준요건 set based)

    matchLabels:               # matchLabels는 {key,value}의 쌍과 매칭, 여기서는 label이 동일한 Pod을 select 함

      app: nginx               # app label 이 nginx 인 pod 을 3개 유지

  template:                    # Pod 생성 시 사용할 template를 정의, 기존의 Pod 정의와 동일

    metadata:                  # Pod 는 labels 필드를 사용해서 app: nginx 이라는 레이블을 붙임

      labels:

        app: nginx

    spec:                      # Pod template 사양 설정 하위에 container 항목은 추가 가능

      containers:              # 실제 사용하려는 컨테이너의 이름(name)과 이미지(image)에 대한 정보

      - name: nginx            # 컨테이너 1개를 생성하고, name 필드를 사용해서 컨테이너에 nginx 이름을 붙임

        image: nginx           # 도커 허브의 nginx 1.7.9 버전 이미지를 실행하는 nginx 컨테이너 1개를 실행하는 것을 나타냄

        ports:                 # pod 내부 컨테이너 port 를 설정 

        - containerPort: 80    # nginx 에 80 port로 접근하겠음

appVersion 설정 참고

v1 : kubernetes에서 발행한 첫 stable release API

apps/v1 : common API 모음, Deployment, RollingUpdate, ReplicaSet을 포함

autoscaling/v1 : pod의 autoscale 기능을 포함하는 API, 현재는 CPU metric을 사용한 scaling만 가능

batch/v1 : 배치 프로세스, job-like task를 위한 배포 api

policy/v1beta1 : pod에 대한 security rule이 정의된 API

 


DaemonSet

kubernetes Cluster 전체에 Pod를 생성할 때 사용하는 controller.

DaemonSet은 보통 모니터링, 로그 수집, 네트워크 CNI 등

Cluster 전체에 Pod를 실행 시켜야하는 상황에 사용됨.

옵션으로 특정 Node 에만 생성되게 지정할 수도 있음.

 

Kubernetes Cluster에 새로운 Worker Node가 추가 되면?

기존 Daemonset 으로 생성된 Pod 가 있는데

새로운 Worker Node가 추가가 되면 DaemonSet으로 생성된 Pod가 자동으로

새로 추가된 Worker Node에 생성됨.

 

Kubernetes Cluster에 동작하던 Worker Node가 사라지면?

해당 Worker Node 에서 동작 중이던 Pod는 

다른 Worker Node로 이동되지 않고 제거됨.

 

 

 

 


Pod 생성되는 과정 정리

 

1. kubectl은 API Server에 Pod생성을 요청

2. API Server는 etcd에 Node에 할당되지 않은 Pod이 있음을 업데이트

3. Scheduler는 etcd의 변경사항을 API Server를 통해 watch

4. Pod을 실행할 Node를 선택해 API Server에 해당 Node에 Pod을 배정하도록 업데이트

5. etcd에 Pod를 배정하도록 했다고 업데이트

6. 해당 Node의 Kubelet은 자신의 Node에 할당되었지만 아직 생성되지 않은 Pod이 있는지 체크

7. 생성되지 않은 Pod이 있으면 명세를 보고 Pod을 생성하기 위해 Docker 컨테이너를 실행

8. Pod의 상태를 주기적으로 API Server에 전달

9. API Server는 전달받은 Pod의 상태를 etcd에 업데이트


 

ReplicaSet 생성되는 과정 정리

 

1. ReplicaSet 명세를 yml파일로 정의하고 kubectl 도구를 이용하여 API Server에 명령을 전달

2. API Server는 새로운 ReplicaSet Object를 etcd에 업데이트

3. Kube Controller에 포함된 ReplicaSet Controller가 ReplicaSet을 감시

4. ReplicaSet에 정의된 Label Selector 조건을 만족하는 Pod이 존재하는지 체크

  - 해당하는 Label의 Pod이 없으면 ReplicaSet의 Pod 템플릿을 보고

  - 새로운 Pod(no assign)을 API Server에 요청

5. API Server는 etcd에 해당 정보를 업데이트

6. Scheduler는 할당되지 않은(no assign) Pod이 있는지 감시

7. 할당되지 않은 Pod이 있으면 조건에 맞는 Node를 찾아 해당 Pod을 할당

8. Kubelet은 자신의 Node에 할당되었지만 아직 생성되지 않은 Pod이 있는지 체크

9. 생성되지 않은 Pod이 있으면 명세를 보고 Pod을 생성하기 위해 Docker 컨테이너를 실행

10. Pod의 상태를 주기적으로 API Server에 전달

11. API Server는 전달받은 Pod의 상태를 etcd에 업데이트

 


 

 

 

 

 


제 글을 복사할 시 출처를 명시해주세요.
글에 오타, 오류가 있다면 댓글로 알려주세요! 바로 수정하겠습니다!


 

 

 

 

참고

쿠버네티스 공식 사이트에서의 설명

https://kubernetes.io/ko/docs/concepts/overview/what-is-kubernetes/

 

쿠버네티스가 나오기까지의 역사 (초급, 중급 난이도의 강의 포함)

https://www.youtube.com/watch?v=8_YnupZqEIE

 

IBM이 설명해주는 kubernetes

https://www.youtube.com/watch?time_continue=25&v=6kQkp-T6wrw&feature=emb_logo

 

쿠버네티스란 ?

https://subicura.com/2019/05/19/kubernetes-basic-1.html

https://www.youtube.com/watch?v=S3FVcdZcZnA&list=LL_EcQ6dgrDsR1lJViaHLQNg&index=2&t=0s

https://www.youtube.com/watch?v=xZ3tcFvbUGc&list=PL9mhQYIlKEhdTu31zyb_QelQMaqFGgASA&index=2

 

kuberenets Desire state 참고

https://www.youtube.com/watch?v=xZ3tcFvbUGc&list=PL9mhQYIlKEhdTu31zyb_QelQMaqFGgASA&index=2

 - 14:30 초 부분

 

실습 따라 하기  (kubernetes 강의)

https://www.youtube.com/watch?v=xZ3tcFvbUGc

 - 정확히 6강부터 Kubernetes 강의임

 

주요 참고

https://bcho.tistory.com/1256

https://kubernetes.io/ko/docs/concepts/workloads/pods/pod-overview/#%ed%8c%8c%eb%93%9c%ec%97%90-%eb%8c%80%ed%95%b4-%ec%9d%b4%ed%95%b4%ed%95%98%ea%b8%b0

https://subicura.com/2019/05/19/kubernetes-basic-1.html

 

쿠버네티스 네트워트 

https://arisu1000.tistory.com/27850

 

object와 controller 의 차이점

https://blog.2dal.com/2018/03/28/kubernetes-01-pod/

https://getoutsidedoor.com/2019/07/27/kubernetes-crd%EC%99%80-operator/

 

Volume 참고

https://arisu1000.tistory.com/27849

 

replicaset 생성 과정

https://blog.2dal.com/2018/04/30/kubernetes-02-replicaset/

 

replication controller 참고

https://kubernetes.io/ko/docs/concepts/workloads/controllers/replicationcontroller/

https://arisu1000.tistory.com/27830

 

replicaSet 참고

https://blog.2dal.com/2018/04/30/kubernetes-02-replicaset/

 

replicaSet 과 replication Controller 차이

https://blusky10.tistory.com/392

https://arisu1000.tistory.com/27831

 

deployments 참고

https://kubernetes.io/ko/docs/concepts/workloads/controllers/deployment/

https://arisu1000.tistory.com/27833

 

Loadbalancer

https://blog.leocat.kr/notes/2019/08/22/translation-kubernetes-nodeport-vs-loadbalancer-vs-ingress

https://kubernetes.io/ko/docs/concepts/services-networking/

부하분산 원리 동영상 강의:  https://www.youtube.com/watch?v=v6TUgqfV3Fo&list=PL9mhQYIlKEhdTu31zyb_QelQMaqFGgASA&index=7

 - 08:54 지점

 

service 란

동영상 강의 :  https://www.youtube.com/watch?v=v6TUgqfV3Fo&list=PL9mhQYIlKEhdTu31zyb_QelQMaqFGgASA&index=7

소스 참고 :  https://github.com/subicura/workshop-k8s-basic

https://kubernetes.io/ko/docs/tutorials/kubernetes-basics/expose/

https://arisu1000.tistory.com/27838

https://arisu1000.tistory.com/27839?category=787056

https://blog.leocat.kr/notes/2019/08/22/translation-kubernetes-nodeport-vs-loadbalancer-vs-ingress

https://www.ibm.com/support/knowledgecenter/SSBS6K_3.2.0/manage_network/kubernetes_types.html

https://bcho.tistory.com/1262

 

동일한 Pods 가 여러개 생성되어야 하는 이유,

https://kubernetes.io/ko/docs/concepts/workloads/pods/pod-lifecycle/

 

Ingress

https://m.blog.naver.com/PostView.nhn?blogId=alice_k106&logNo=221502890249&proxyReferer=https%3A%2F%2Fwww.google.com%2F

https://arisu1000.tistory.com/27840

 

volume 참고

https://bcho.tistory.com/1259

 

kubernetes Master Node HA (이중화) 구성

https://fliedcat.tistory.com/170

https://skysoo1111.tistory.com/47

반응형

'클라우드 > Kubernetes' 카테고리의 다른 글

06. Kubernetes Network (ClusterIP, NodePort)  (0) 2020.08.09
05. Kuberentes Network 이론  (2) 2020.08.09
04. Kubernetes Pod 더 자세히 알아보기  (2) 2020.08.07
03. Kubernetes 설치 과정  (0) 2020.08.07
02. Kubernetes Addon  (0) 2020.08.05