DaemonSet #
DaemonSet memastikan satu copy Pod berjalan di setiap node — atau di setiap node yang memenuhi kriteria tertentu. Ketika node baru bergabung ke cluster, DaemonSet otomatis membuat Pod di node tersebut. Ketika node dihapus, Pod-nya juga dihapus. Ini adalah resource yang tepat untuk semua kebutuhan di mana setiap node perlu menjalankan agen tertentu — log collector, monitoring agent, network plugin, atau storage driver.
Cara Kerja DaemonSet #
DaemonSet tidak menggunakan scheduler Kubernetes untuk menentukan di mana Pod berjalan. Scheduler biasa memilih node terbaik berdasarkan resource. DaemonSet lebih sederhana: satu Pod per node, titik.
Cluster dengan 4 worker node:
DaemonSet "node-exporter" (monitoring agent):
worker-1 → Pod "node-exporter-a1b2"
worker-2 → Pod "node-exporter-c3d4"
worker-3 → Pod "node-exporter-e5f6"
worker-4 → Pod "node-exporter-g7h8"
Worker node baru bergabung:
worker-5 → Pod "node-exporter-i9j0" ← dibuat otomatis
Worker node dihapus:
worker-3 dihapus → Pod "node-exporter-e5f6" juga hilang
Struktur Manifest DaemonSet #
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: node-exporter
namespace: monitoring
labels:
app: node-exporter
spec:
selector:
matchLabels:
app: node-exporter
updateStrategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 1 # update satu node dalam satu waktu
template:
metadata:
labels:
app: node-exporter
spec:
# Akses ke filesystem dan informasi host
hostPID: false
hostNetwork: false # true jika perlu akses network host langsung
containers:
- name: node-exporter
image: prom/node-exporter:v1.7.0
ports:
- containerPort: 9100
hostPort: 9100 # bind ke port host langsung
args:
- --path.rootfs=/host
volumeMounts:
- name: host-root
mountPath: /host
readOnly: true
resources:
requests:
cpu: "50m"
memory: "64Mi"
limits:
cpu: "200m"
memory: "180Mi"
volumes:
- name: host-root
hostPath:
path: / # akses ke root filesystem host
Use Case: Log Collection #
Log collector seperti Fluentd atau Promtail perlu berjalan di setiap node untuk mengumpulkan log dari semua container yang berjalan di node tersebut:
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: fluentd
namespace: logging
spec:
selector:
matchLabels:
app: fluentd
template:
metadata:
labels:
app: fluentd
spec:
serviceAccountName: fluentd # butuh permission untuk baca metadata Pod
containers:
- name: fluentd
image: fluent/fluentd-kubernetes-daemonset:v1.16
env:
- name: FLUENT_ELASTICSEARCH_HOST
value: "elasticsearch-service"
volumeMounts:
# Mount direktori log container dari host
- name: varlog
mountPath: /var/log
- name: varlibdockercontainers
mountPath: /var/lib/docker/containers
readOnly: true
volumes:
- name: varlog
hostPath:
path: /var/log
- name: varlibdockercontainers
hostPath:
path: /var/lib/docker/containers
Use Case: Network Plugin (CNI) #
Plugin jaringan Kubernetes seperti Calico, Flannel, dan Cilium dijalankan sebagai DaemonSet. Mereka perlu berjalan di setiap node untuk mengelola network interface dan routing rules di level node.
# Contoh: Calico node agent sebagai DaemonSet
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: calico-node
namespace: kube-system
spec:
template:
spec:
hostNetwork: true # perlu akses ke network namespace host
containers:
- name: calico-node
image: calico/node:v3.26
securityContext:
privileged: true # perlu akses tinggi untuk kelola network
volumeMounts:
- mountPath: /lib/modules
name: lib-modules
readOnly: true
- mountPath: /run/xtables.lock
name: xtables-lock
volumes:
- name: lib-modules
hostPath:
path: /lib/modules
- name: xtables-lock
hostPath:
path: /run/xtables.lock
DaemonSet di Control Plane Node #
Secara default, DaemonSet tidak menjadwalkan Pod ke control plane node — control plane node biasanya punya taint node-role.kubernetes.io/control-plane:NoSchedule yang mencegah workload biasa berjalan di sana.
Untuk DaemonSet yang perlu berjalan di semua node termasuk control plane (misalnya network plugin atau monitoring):
tolerations:
# Tolerate taint di control plane node
- key: node-role.kubernetes.io/control-plane
operator: Exists
effect: NoSchedule
# Untuk cluster lama yang masih pakai "master"
- key: node-role.kubernetes.io/master
operator: Exists
effect: NoSchedule
# Tolerate node yang sedang not-ready
- key: node.kubernetes.io/not-ready
operator: Exists
effect: NoExecute
tolerationSeconds: 300
DaemonSet di Subset Node #
DaemonSet tidak harus berjalan di semua node. Kamu bisa membatasi ke node tertentu menggunakan nodeSelector atau nodeAffinity:
# Hanya node dengan GPU
nodeSelector:
hardware: gpu
# Atau dengan nodeAffinity yang lebih ekspresif
affinity:
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: node-type
operator: In
values:
- high-memory
- gpu-enabled
Contoh penggunaan: DaemonSet untuk GPU monitoring yang hanya perlu berjalan di node yang punya GPU, bukan semua node.
Update Strategy #
DaemonSet mendukung dua update strategy:
RollingUpdate (default) — update node satu per satu dengan jumlah yang dikontrol:
updateStrategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 1 # default: 1
# maxSurge: 0 # tersedia di Kubernetes 1.22+
OnDelete — Pod di-update hanya ketika dihapus manual; kamu yang kontrol kapan update terjadi per node:
updateStrategy:
type: OnDelete
OnDelete berguna ketika update perlu dilakukan dengan hati-hati, misalnya kernel module atau network plugin yang bisa mempengaruhi seluruh traffic di node tersebut.
Monitoring DaemonSet #
# Lihat status DaemonSet
kubectl get daemonset -n monitoring
# Output:
# NAME DESIRED CURRENT READY UP-TO-DATE AVAILABLE NODE SELECTOR
# node-exporter 4 4 4 4 4 <none>
# DESIRED = jumlah node yang memenuhi syarat
# CURRENT = jumlah Pod yang sudah ada
# READY = jumlah Pod yang siap menerima traffic
# Jika DESIRED != CURRENT atau CURRENT != READY, ada masalah
kubectl describe daemonset node-exporter -n monitoring
# Lihat Pod DaemonSet di semua node
kubectl get pods -n monitoring -o wide | grep node-exporter
Ringkasan #
- Satu Pod per node, otomatis — DaemonSet tidak menggunakan scheduler biasa; Pod dibuat di setiap node yang memenuhi syarat saat node bergabung, dihapus saat node pergi.
- Use case utama: node-level agent — log collector, monitoring agent, network plugin, storage driver; semua komponen yang perlu berjalan di setiap node untuk beroperasi.
- hostPath dan hostNetwork untuk akses host — DaemonSet sering butuh akses ke filesystem dan network namespace host; perlu dipertimbangkan implikasi keamanannya.
- Toleration untuk control plane — tambahkan toleration eksplisit jika DaemonSet perlu berjalan di control plane node.
- nodeSelector untuk subset node — tidak semua DaemonSet harus di semua node; batasi ke node tertentu jika fungsionalitasnya spesifik (GPU node, high-memory node).
- Resource limits tetap wajib — DaemonSet berjalan di setiap node, jadi resource yang dipakai aggregate sangat signifikan; tetapkan limits yang ketat untuk mencegah resource starvation di node.