BACKEND/Docker & Kubernetes

Kubernetes DaemonSet, 제대로 이해하기

gngsn 2024. 4. 1. 13:19

본 포스팅에서는 Kubernetes의 DaemonSet의 개념을 이해하는 목표를 가집니다.

 

 

🔗  Kubernetes Series

모든 Kubernetes 시리즈를 확인하시려면 위를 참고해 주세요.

 

 

 


 

 

DaemonSets

DaemonSet은 일부 혹은 모든 노드에 동일한 Pod (copy of a Pod) 가 하나씩 실행되도록 보장합니다.

 

 

 

클러스터에 새 노드가 추가될 때마다 Pod 복제본이 자동으로 해당 노드에 추가되고,

노드가 제거되면 Pod는 Garbage Collection의 대상이 되어 자동으로 제거됩니다.

 

 

 

 

대부분의 일반적인 경우엔,

ReplicaSet과 Deployment을 통해 여러 Worker Node에서 애플리케이션을 복제하면서,

Cluster 내 다양한 노드에 다양한 포드를 배포할 수 있었습니다.

 

Before Deployment

  🟠🔴           🟡🟠            🟡🟢            🟢🟢
  🔴🟠           🟠🟠            🟠🟡            🟡🟢
Node 1      Node 2      Node 3        Node 4

 

🔴🟠🟡🟢 는 각 Node에 위치한 Pod를 의미합니다.

 

 

DaemonSet 은 ReplicaSet 와 비슷하게 여러 개의 인스턴스 Pod를 배포할 수 있게 하는데,

클러스터의 노드마다 단 하나의 Pod를 실행합니다.

 

After Deployment

    ⚫️           ⚫️               ⚫️            ⚫️

  🟠🔴        🟡🟠          🟡🟢         🟢🟢
  🔴🟠        🟠🟠          🟠🟡         🟡🟢
Node 1    Node 2    Node 3    Node 4

 

⚫️ 는 각 Node에 위치한 DaemonSet Pod를 의미합니다.

 

 

DaemonSet은 Pod의 복제본을 클러스터 내 모든 노드에 항상 존재하게 합니다.

일반적으로, DaemonSet는 다음과 같은 용도로 사용되곤 합니다.

 

✔️ 모든 노드에서 실행되는 클러스터 스토리지

✔️ 모든 노드에서 실행되는 로그 수집

✔️ 모든 노드에서 실행되는 노드 모니터링

 

단순하게, 모든 노드에 존재하는 하나의 DaemonSet가 여러 타입의 daemon 처리를 위해 사용되곤 합니다.

더 복잡한 설정을 위해, 하나의 데몬 처리를 위해 여러 DaemonSet을 사용할 수 있지만,

각 하드웨어 유형에 따라 서로 다른 플래그, 메모리, CPU 요구가 달라집니다.

 

 

 

 

 

Use cases

1. Monitoring or Logs Viewer

데몬셋을 활용할 수 있는 아주 적합한 예시들이 존재하는데요.

바로, Monitoring 과 Logs Viewer입니다.

 

Monitoring 에이전트나 Logs Collector를 클러스터 내 각 노드에 배포하면,

데몬셋은 모든 노드에 한 Pod로 배치하기 때문에 최적입니다.

 

클러스터에 변화 생기면, 데몬셋이 알아서 제거/추가하기 때문에 따로 관리할 필요가 없습니다.

 

 

 

2. kube-proxy

kube-proxy 는 DaemonSet의 좋은 예시입니다.

 

 

 

kube-proxy 구성 요소는 클러스터에서 DaemonSet으로 배포될 수 있습니다.

 

 

 

3. Networking

weave-net 같은 네트워킹 솔루션은,

해당 에이전트가 클러스터 내 각 노드에 배치되어야 하기 때문에 데몬셋을 활용하기 적합합니다.

 

 

 

 

 

DaemonSet Definition

데몬셋을 생성은 ReplicaSet 생성 정의와 비슷합니다.

 

apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: monitoring-daemon
spec:
  selector:
    matchLabels:
      app: monitoring-agent
  template:
    metadata:
      labels:
        app: monitoring-agent
    spec:
      containers:
      - name: monitoring-agent
        image: nginx

 

 

 

ReplicaSet의 selector에 지정한 레이블(.spec.selector.matchLabels)과,

Pod template 하위의 레이블이 일치하는지 확인 필요합니다.

 

 

 

 

Command

정의한 파일을 기반으로 DaemonSet을 생성해보겠습니다.

 

 

✔️ 1. kubectl create 명령어로 DaemonSet 생성

❯ kubectl create -f daemon-set-definition.yaml
daemonset.apps/monitoring-daemon created
 

 

 

✔️ 2. kubectl get 명령어로 DaemonSet 조회

❯ kubectl get daemonsets
NAME                DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR   AGE
monitoring-daemon   1         1         1       1            1           <none>          2m21s
 

 

 

✔️ 3. kubectl describe 명령어로 DaemonSet 상세 조회

❯ kubectl describe daemonsets monitoring-daemon                                                                                                                ─╯
Name:           monitoring-daemon
Selector:       app=monitoring-agent
Node-Selector:  <none>
Labels:         <none>
Annotations:    deprecated.daemonset.template.generation: 1
Desired Number of Nodes Scheduled: 1
Current Number of Nodes Scheduled: 1
Number of Nodes Scheduled with Up-to-date Pods: 1
Number of Nodes Scheduled with Available Pods: 1
Number of Nodes Misscheduled: 0
Pods Status:  1 Running / 0 Waiting / 0 Succeeded / 0 Failed
Pod Template:
  Labels:  app=monitoring-agent
  Containers:
   monitoring-agent:
    Image:        nginx
    Port:         <none>
    Host Port:    <none>
    Environment:  <none>
    Mounts:       <none>
  Volumes:        <none>
Events:
  Type    Reason            Age   From                  Message
  ----    ------            ----  ----                  -------
  Normal  SuccessfulCreate  3m7s  daemonset-controller  Created pod: monitoring-daemon-vtnsp

 

 

 

 

 

 

How does DaemonSet work?

DaemonSet 은 어떻게 동작할까요?

어떻게 모든 노드에 포드가 있는지 보장할 수 있을까요?

 

클러스터의 각 노드에 포드를 지정해야 한다면, Node Affinity 를 사용할 수 있습니다.

혹은, 각 Pod의 스팩 정의에 nodeName 속성 설정할 수도 있습니다.

 

Affinity:  Node 1    Node 2   Node 3   Node 4
              ⚫️      ⚫️       ⚫️       ⚫️
              ↓       ↓️        ↓       ↓️
              🟥️      🟧️       🟨       🟩
            Node 1   Node 2   Node 3   Node 4 
 
 
 

쿠버네티스 버전에 따라 동작에 조금 차이가 있습니다.

 

< v.1.12: Pod가 생성될 때 각 노드에 자동 배치

>= v.1.12: NodeAffinity + default scheduler

 

조금 더 자세한 내용은 How Daemon Pods are scheduled 을 참고 하시길 바랍니다.

 

 

 

 

 

그럼 여기까지, 쿠버네티스의 DaemonSets에 대해 알아보았습니다.

 

 

 

 

 

| Reference |

 

🔗  Kubernetes.io - Official Docs

🔗  Udemy: certified-kubernetes-administrator-with-practice-tests