Kubernetes는 컨테이너화된 애플리케이션을 자동으로 배포, 스케일링 및 관리하기 위한 오픈 소스 플랫폼이다.
Docker 가 정해진 레시피를 토대로 만들어진 요리라면 Kubernetes는 주방장이라고 볼 수 있다. 이 Kubernetes 주방장이 요리사들을 관리하며 어떤 요리사가 어떤 요리를 어떻게 해야 하는 지 지시한다.
Kubernetes 의 대표적인 기능
[자동 스케일링]
쿠버네티스는 애플리케이션의 트랙픽이 증가할 때 자동으로 파드의 수를 늘리고, 트래픽이 감소할 때는 줄여주는 자동 스케일링 기능을 제공한다. CPU 사용률, 메모리 사용량 등 다양한 매트릭을 기반으로 동작한다.
이러한 기능 덕분에 트랙픽의 변화에 따른 장애 상황을 방지하고, 리소스를 효율적으로 사용할 수 있다. 이로 인해 운영 비용을 절약하면서도 높은 서비스 가용성을 유지할 수 있다.
[자동화된 복구]
쿠버네티스는 컨테이너나 노드에 문제가 발생한 경우, 자동으로 북구 작업을 수행한다. 예를 들어, 컨테이너가 오류로 중지될 경우 쿠버네티스는 해당 컨테이너를 재시작하고, 노드에 장애가 발생할 경우 해당 노드의 작업을 안정적인 다른 노드로 이동시킨다.
이러한 기능은 수동 개입 없이도 장애 상황을 자동으로 복구할 수 있어 운영 팀의 부담을 줄여준다.
[무중단 업데이트]
롤링 업데이트: 정해진 비율만큼의 파드만 점직적으로 배포
기차의 객차를 한 대씩 새로운 모델로 교체하는 것으로 생각. 처음에는 한 대의 객차만 교체하고, 그 다음 객차를 교체하고, 이런 식으로 전체 객차를 새로운 모델로 바꾸는 것. 이 과정에서 기차는 계속 운행 중
블루-그린 배포: 블루는 현재 운영 중인 버전, 그린은 새로 배포할 버전이다. 두 버전을 동시에 구동하되, 트래픽은 한 버전(블루)만 받게 설정. 테스트와 검증 후에 트랙픽을 새 버전(그린)으로 전환한다. 문제가 발생하면 빠르게 이전 버전(블루)로 트래픽 전환.
카나리 배포: 새로운 버전의 파드를 일부만 배포하여 실제 사용자 트래픽을 받게 한다. 문제 없이 운영되면, 전체 서비스를 새 버전으로 점진적으로 업데이트한다. 문제가 발생하면 새 버전의 배포를 중단하고, 전체 트래픽을 안정적인 이전 버전으로 유지한다.
롤링 업데이트 vs 카나리 배포
롤링 업데이트는 새로운 버전의 애플리케이션을 점진적으로 배포하면서, 동시에 이전 버전의 인스턴스를 제거한다. 이러한 방식은 새로운 버전의 애플리케이션에 대한 확신이 있을 때 주로 사용된다.
카나리 배포는 새 버전의 애플리케이션을 일부만 배포하여, 초기 반응 및 피드백을 확인한다. 만약 새로운 버전에 문제가 발생되면, 큰 영향을 받지 않고 원래의 버전으로 돌아갈 수 있다.
Kubernetes 구성 요소 간 통신 아키텍처
1. 사용자 요청: 사용자나 시스템 관리자는 kubectl 명령어를 사용해 쿠버네티스 API 서버에 요청을 보냄. 이 과정에서 kubectl 은 사용자의 kubeconfig 파일(~/.kube/config)을 참조하여 API 서버의 URL과 인증 정보를 알아냄
2. etcd 데이터베이스 조회: 쿠버네티스 클러스터의 모든 구성 정보와 상태 정보를 저장하는 분산 key-value 스토어. 이 etcd가 다운되면 Kubernetes 클러스터가 제대로 동작하지 않기 떄문에 높은 신뢰성을 제공해야 한다.
3. 컨트롤러 매니저: 클러스터의 다양한 컨트롤러 관리, 원하는 상태(desired state)와 현재 상태의 차이를 감지하고 필요한 조치를 취함
주요 컨트롤러로는 노드 컨트롤러, 레플리케이션 컨트롤러, 엔드포인트 컨트롤러 등이 있다.
4. 스케줄러: 생성된 파드에 대한 가장 적합한 노드를 결정하고 할당하는 역할
5. kubelet: 각 노드에서 실행되는 에이전트로, 파드의 생명 주기를 관리하며 컨테이너 런타임과 통신하여 컨테이너를 시작, 중지하는 역할을 함
- PodSpec의 해석
- 컨테이너 실행
- 컨테이너의 생명 주기관리
- 컨테이너 상태 보고(kube-apiserver 를 통해 마스터 노드와 통신)
- 로컬 노드 모니터링
6. 컨테이너 런타임: 실제로 컨테이너를 실행하는 소프트웨어, 대표적으로 Docker 가 있다.
7. pod: 쿠버네티스의 기본 배포 단위로, 하나 이상의 컨테이너로 구성
8. kube-proxy: 클러스터 내부의 서비스에 대한 네트워크 트래픽을 처리하고 로드 밸런싱을 수행하는 역할
- 워커 노드에서 네트워크 프록시 관리
- 서비스에 대한 네트워크 요청을 적절한 파드로 라우팅
9. service: 파드의 집합에 대한 접근을 가능하게 하는 로드 밸러서나 IP 주소를 제공
파드의 생명 주기
1. kubectl 을 통해 API 서버에 파드 생성 요청
2. API 서버에 전달된 내용이 있으면 API 서버는 etcd에 전달된 내용을 모두 기록해 클러스터의 상태 값을 최신으로 유지.
따라서 각 요소가 상태를 업데이트할 때마다 모두 API 서버를 통해 etcd에 기록
3. API 서버에 파드 생성이 요청된 것을 컨트롤러 매니저가 인지하면 컨트롤러 매니저는 파드를 생성하고 이 상태를 API 서버에 전달
4. API 서버에 파드가 생성됐다는 정보를 스케줄러가 인지. 스케줄러는 생성된 파드를 어떤 워커 노드에 적용할지 조건을 고려해 결정
5. API 서버에 전달된 정보대로 지정한 워커 노드에 파드가 속해 있는지 스케줄러가 kubelet 으로 확인
6. kubelet 에서 컨테이너 런타임으로 파드 생성 요청
7. 파드 생성
💡쿠버네티스는 작업을 순서대로 진행하는 워크플로 구조가 아니라 선언적인 시스템을 가지고 있습니다.
즉, 각 요소가 추구하는 상태를 선언하면 현재 상태와 맞는지 점검하고 그에 맞추려고 노력하는 구조로 되어 있다는 뜻
따라서 추구하는 상태를 API 서버에 선언하면 다른 요소들이 API 서버에 와서 현재 상태와 비교하고 그에 맞게 상태를 변경하려고 함. API 는 현재 상태 값을 가지고 있는데, 이것을 보존해야 해서 etcd가 필요. API 서버와 etcd는 거의 한몸처럼 움직이도록 설계됨.
Deployment vs Replicaset
모두 애플리케이션을 스케일 아웃하고 업데이트하기 위한 리소스이며 controller이다.
[Deployment]
정의: Deployment는 상태를 선언적으로 관리하기 위한 리소스
기능:
- 애플리케이션의 신규 버전을 롤링 업데이트를 통해 안전하게 배포
- 롤백 기능을 제공하여 이전 버전으로 쉽게 되돌릴 수 있다.
- 다른 업데이트 전략(ex. Blue/Green, Canary)을 지원
관리수준: Deployment는 Replicaset을 관리하며, 따라서 더 높은 수준의 추상화 제공
[Replicaset]
정의: Replicaset은 지정된 수의 Pod 복사본이 항상 실행되도록 보장하는 controller이다.
기능:
- 애플리케이션의 스케일링 관리
- 단독으로 사용할 때 롤링 업데이트나 롤백과 같은 기능을 제공하지 않음
관리수준: Replicaset은 Pod를 직접 관리
⛔️ 차이점
- Deployment는 Replicaset위에 구축되어 더 높은 수준의 기능 제공. 이를 통해 사용자는 애플리케이션의 업데이트와 롤백을 쉽게 관리 가능
- Replicaset은 기본적으로 Pod의 수를 관리하는 역할
- Deployment는 내부적으로 Replicaset 을 사용하여 Pod 관리
일반적으로, Deployment를 사용하여 애플리케이션을 배포하는 것이 바람직. Deployment는 애플리케이션의 업데이트와 스케일링을 더욱 간단하고 효율적으로 관리할 수 있게 도와주는 훌륭한 추상화 제공
Deployment 는 내부적으로 Replicaset 을 관리하기 때문에 Replicaset 리소스를 직접 정의할 필요는 없다.
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-app-deployment
spec:
replicas: 3
selector:
matchLabels:
app: my-app
template:
metadata:
labels:
app: my-app
spec:
containers:
- name: my-app-container
image: my-app-image:v1
파드의 자동 복구
파드는 언제든지 죽을 수 있다. 다시 생성되는 과정은 다음과 같다.
1. 파드의 상태 모니터링
- kubelet또는 kubernetes API서버는 클러스터 내의 모든 파드의 상태를 주기적으로 확인
- Replicaset 컨트롤러도 클러스터의 상태 모니터링
(kubelet은 노드 및 노드의 컨테이너 상태 관리, Replicaset은 클러스터 수준에서 파드의 복제본 수 관리)
2. 파드 상태의 변경 감지
- kubelet이 감지하고 API 서버에 요청
- 파드가 속한 컨트롤러는 종료된 파드 감지
3. 파드의 상태 업데이트
- 파드의 상태는 API 서버에 의해 업데이트 되고, 파드의 상태가 Terminating 또는 Failed 로 변경
4. 복제본 개수 확인
- Replicaset 컨트롤러는 현재 실행 중인 파드의 수와 원하는 복제본 수 비교
- 파드의 수가 원하는 복제본 수보다 적으면, 컨트롤러는 새 파드를 스케줄링하여 시작
5. 새 파드 스케즐링
- 스케줄러는 새 파드를 적합한 노드에 스케줄링
- 스케줄러가 노드를 선택하면, 해당 노드의 kubelet이 새 파드 시작
6. 파드 실행
- kubelet은 새 파드에 대한 컨테이너 이미지를 Pull 하고, 컨테이너 실행
- 이 과정이 완료되면, 새 파드는 실행 상태가 되어 작동 시작
데몬셋(DaemonSet)
Kubernetes의 데몬셋은 클러스터의 모든 노드(또는 특정 노드) 에 특정 파드를 하나씩 실행되도록 보장. Daemonset은 주로 시스템 수준의 작업을 수행하는 파드를 실행하는데 사용. 새 노드가 클러스터에 추가되면 해당 노드에서 Daemonset 에 정의된 파드가 자동으로 시작됨
[데몬셋의 주요 사용 사례]
1. 노드 모니터링: 각 노드에서 실행되어 노드 및 클러스테 대한 메트릭스 수집
2. 로깅: 각 노드에서 로그를 수집하고 중앙 로깅 솔루션에 전달
3. 네트워크 설정: 네트워크 관련 작업을 수행하거나 노드에 네트워크 설정 적용
[데몬셋 작동 방식]
- 데몬셋은 클러스터의 모든 노드에 파드를 자동 배포
- 새 노드가 클러스터에 추가되면, 데몬셋은 해당 노드에 파드 추가
- 노드가 클러스터에서 제거되면, 데몬셋에 의해 생성된 파드도 자동 제거
- 데몬셋에 의해 생성된 파드는 수동으로 제거되어서는 안됨. 만약 파드 삭제하면, 데몬셋은 삭제된 파드를 자동으로 다시 생성
'Kubernetes' 카테고리의 다른 글
[Udemy] DevOps: Kubernetes 완전정복 | LIM (0) | 2024.04.14 |
---|
댓글