Phần 1 — Kubernetes là gì? Tổng quan và kiến trúc
Ý kiến
0
Chưa có ý kiến nào. Hãy là người đầu tiên chia sẻ!
Chưa có ý kiến nào. Hãy là người đầu tiên chia sẻ!
Phần cuối series K8s: Cluster API (CAPI) quản lý cluster bằng K8s API, FinOps với OpenCost + Karpenter + right-sizing, AI/ML workloads (GPU, Kubeflow, KServe, vLLM, Argo Workflows, gang scheduling), Edge K8s và WebAssembly.
Multi-tenancy K8s (soft: namespace+RBAC+Quota, HNC, Capsule, vCluster; hard: cluster riêng) và multi-cluster: management cluster, GitOps ApplicationSet, Cluster API, Karmada, Crossplane, observability liên cluster.
Service Mesh chuyên sâu cho K8s: Istio (sidecar + ambient), Linkerd (proxy Rust nhẹ), Cilium Service Mesh (eBPF sidecarless) — mTLS, VirtualService, AuthorizationPolicy, canary, mirror, multi-cluster, đo overhead, khi không nên dùng mesh.
Series Kubernetes Toàn Tập — 13 phần:
Phần 1 — Kubernetes là gì? Tổng quan và kiến trúc ← bạn đang đọc
Phần 2 — Cài đặt cluster: minikube, kind, kubeadm và kubectl
Phần 3 — Workloads: Pod, ReplicaSet, Deployment, StatefulSet, DaemonSet, Job/CronJob
Phần 6 — Configuration: ConfigMap, Secret và projected volumes
Phần 7 — Security: RBAC, ServiceAccount, SecurityContext, Pod Security
Phần 8 — Scheduling & Autoscaling: requests/limits, affinity, taints, HPA/VPA/CA
Phần 10 — Production: Observability, Backup, Upgrade, Disaster Recovery
Kubernetes (viết tắt là K8s — số 8 là số ký tự giữa K và s) là một open-source container orchestration platform dùng để tự động hoá việc triển khai, scale và quản lý containerized applications.
Tên gọi Kubernetes xuất phát từ tiếng Hy Lạp, nghĩa là người lái tàu hoặc hoa tiêu. Google open-source dự án này năm 2014, dựa trên hệ thống nội bộ Borg đã chạy hơn 10 năm để quản lý hàng tỷ container mỗi tuần. Hiện K8s thuộc về CNCF (Cloud Native Computing Foundation) và đã trở thành de facto standard cho container orchestration.
Để hiểu vì sao K8s ra đời, hãy nhìn lại lịch sử triển khai ứng dụng:
| Thời kỳ | Cách triển khai | Vấn đề |
|---|---|---|
| Traditional | App chạy trực tiếp trên physical server | Không cô lập tài nguyên, conflict dependencies, tốn server, scale chậm |
| Virtualization | VM chạy trên hypervisor (VMware, KVM, Hyper-V) | Cô lập tốt nhưng nặng (mỗi VM một OS), boot chậm, image lớn (GB) |
| Container | Docker chia sẻ kernel host, đóng gói app + dependencies | Nhẹ, boot nhanh, portable — nhưng tự quản lý hàng trăm container thì không khả thi |
Container giải quyết được vấn đề build once, run anywhere. Nhưng khi bạn có hàng chục, hàng trăm container trải trên nhiều máy, bạn lập tức gặp các câu hỏi sau:
Khi một container chết, ai sẽ restart nó?
Khi traffic tăng, ai sẽ scale thêm container? Trên máy nào?
Làm sao để các container giao tiếp với nhau qua mạng?
Làm sao deploy version mới mà không downtime?
Làm sao chia config, secret cho hàng trăm container đang chạy?
Khi node chết, ai sẽ schedule lại workload sang node khác?
Đó chính là việc của Kubernetes.
Theo tài liệu chính thức tại kubernetes.io, K8s cung cấp:
Service discovery và load balancing — expose container qua DNS name hoặc IP riêng, tự load balance.
Storage orchestration — tự mount storage (local, NFS, cloud disk) khi pod cần.
Automated rollout/rollback — deploy version mới từ từ, rollback ngay khi lỗi.
Self-healing — restart container chết, replace container không healthy, kill container không response health check.
Bin packing — tự nhét workload vào node cho tối ưu CPU/RAM.
Secret và configuration management — quản lý password, OAuth token, SSH key mà không cần rebuild image.
Horizontal scaling — scale app theo command, theo UI, hoặc tự động theo CPU/memory.
Batch execution — chạy job, cron job, replace container fail nếu cần.
IPv4/IPv6 dual-stack, declarative API, extensible qua CRD.
Cũng quan trọng không kém: K8s không phải một PaaS truyền thống. K8s không:
Không giới hạn loại app — bạn chạy được mọi workload chạy được trong container (stateless, stateful, batch, ML, database…).
Không deploy source code và không build image — bạn vẫn cần CI/CD pipeline riêng.
Không cung cấp application-level services như database, cache, message queue — mặc dù bạn có thể chạy chúng trên K8s.
Không cung cấp logging, monitoring, alerting tích hợp — bạn lắp riêng (Prometheus, Loki, Grafana, OTel…).
Không cung cấp config language/system (như Jsonnet, Helm) — bạn có thể chọn tuỳ ý.
Không tự thay thế ý chí của bạn — K8s thực thi desired state bạn khai báo. Khai báo sai, K8s vẫn làm.
Một Kubernetes cluster gồm tập hợp các máy gọi là nodes, chia thành hai vai trò chính:
Control Plane — bộ não, đưa ra quyết định toàn cluster.
Worker Nodes — nơi workload thật sự chạy (containers/Pods).
┌──────────────────────────────────────┐
│ CONTROL PLANE │
│ │
│ ┌──────────────┐ ┌─────────────┐ │
kubectl ─────────────┼─► │ API Server │◄►│ etcd │ │
│ └──────┬───────┘ └─────────────┘ │
│ │ │
│ ┌──────▼────────┐ ┌────────────┐ │
│ │ Scheduler │ │ Controller │ │
│ │ │ │ Manager │ │
│ └───────────────┘ └────────────┘ │
└─────────────────┬────────────────────┘
│
┌──────────────────────┼──────────────────────┐
│ │ │
┌─────▼──────┐ ┌─────▼──────┐ ┌─────▼──────┐
│ Node 1 │ │ Node 2 │ │ Node N │
│ │ │ │ │ │
│ kubelet │ │ kubelet │ │ kubelet │
│ kube-proxy │ │ kube-proxy │ │ kube-proxy │
│ Runtime │ │ Runtime │ │ Runtime │
│ │ │ │ │ │
│ ┌──────┐ │ │ ┌──────┐ │ │ ┌──────┐ │
│ │ Pod │ │ │ │ Pod │ │ │ │ Pod │ │
│ └──────┘ │ │ └──────┘ │ │ └──────┘ │
└────────────┘ └────────────┘ └────────────┘
Là cửa ngõ duy nhất vào cluster. Mọi command (qua kubectl, qua client library, qua component khác) đều đi qua API Server. API Server expose Kubernetes REST API, validate request, lưu state vào etcd, và là điểm watch cho các controller khác.
Đây là component duy nhất giao tiếp trực tiếp với etcd — mọi thứ khác phải hỏi qua API Server. Thiết kế này giúp encapsulate backing store và cho phép scale horizontally.
Một distributed key-value store dùng làm backing store cho toàn bộ cluster data. Mọi object Kubernetes — Pod, Service, ConfigMap, Secret, Node… — đều lưu trong etcd.
Vì etcd là source of truth nên nó tối quan trọng:
Production phải chạy HA cluster với số node lẻ (thường 3 hoặc 5) để đạt quorum.
Phải backup snapshot định kỳ. Mất etcd = mất cluster (dù pod vẫn chạy, không ai control được nữa).
Nên có disk SSD riêng, latency thấp.
Theo dõi các Pod chưa được gán node và quyết định Pod đó nên chạy ở node nào. Quyết định dựa vào:
Resource requirements (CPU, memory).
Hardware/software/policy constraints.
Affinity và anti-affinity rules.
Data locality.
Inter-workload interference, deadlines.
Scheduler chỉ quyết định — việc khởi chạy là của kubelet.
Chạy nhiều controller trong một process. Mỗi controller là một control loop theo dõi state cluster qua API Server và thực hiện thay đổi để đưa state về desired state. Ví dụ:
Node controller — phát hiện node down.
Job controller — tạo Pod cho Job và theo dõi đến khi hoàn thành.
EndpointSlice controller — kết nối Service ↔ Pod.
ServiceAccount controller — tạo default ServiceAccount cho namespace mới.
Tách phần logic phụ thuộc cloud provider (AWS, GCP, Azure…) khỏi controller-manager chính. Quản lý LoadBalancer, Route, Node lifecycle với cloud API. Cluster on-prem có thể không có component này.
Một agent chạy trên mọi node. Kubelet đảm bảo các container được mô tả trong PodSpec đang chạy đúng và healthy. Nó:
Nhận PodSpec từ API Server (hoặc static file).
Gọi container runtime để pull image, tạo container.
Mount volume, inject secret/configmap.
Chạy liveness/readiness/startup probe.
Report status pod và node lên API Server.
Kubelet không quản lý container không phải do K8s tạo ra.
Một network proxy chạy trên mọi node, implement phần Service của K8s. Nó duy trì network rules (qua iptables, ipvs, hoặc nftables) để traffic đến ClusterIP/NodePort/LoadBalancer được route đúng đến Pod backend.
Một số CNI (như Cilium) có thể thay thế kube-proxy hoàn toàn bằng eBPF.
Phần mềm thực sự chạy container. Kubernetes giao tiếp với runtime qua CRI (Container Runtime Interface). Các implementation phổ biến:
containerd — runtime mặc định, đến từ Docker, gọn nhẹ.
CRI-O — runtime nhẹ chuyên cho K8s, mặc định của OpenShift.
Docker Engine — đã deprecated từ K8s 1.24 (dockershim bị remove). Vẫn có thể dùng qua cri-dockerd nhưng không khuyến nghị.
Kubernetes là một declarative system. Bạn không ra lệnh chạy lệnh A rồi lệnh B — bạn khai báo desired state, và K8s lo phần thực thi.
Mỗi object trong K8s có cấu trúc YAML chuẩn 4 phần:
apiVersion: apps/v1 # version của API
kind: Deployment # loại object
metadata: # tên, namespace, labels, annotations
name: nginx
namespace: default
labels:
app: nginx
spec: # desired state — phần bạn khai báo
replicas: 3
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.27
ports:
- containerPort: 80
Sau khi apply, object thật sự có thêm phần status do K8s ghi vào — cho biết current state ra sao.
| Object | Mục đích |
|---|---|
Pod | Đơn vị nhỏ nhất, 1 hoặc nhiều container dùng chung network + storage |
ReplicaSet | Đảm bảo N replicas của Pod luôn chạy |
Deployment | Quản lý ReplicaSet, hỗ trợ rolling update/rollback |
StatefulSet | Như Deployment nhưng pod có identity ổn định + storage riêng (DB, queue) |
DaemonSet | Đảm bảo mọi node có 1 pod (log agent, network agent) |
Job / CronJob | Batch one-off hoặc theo lịch |
Service | Stable network endpoint cho group Pod |
Ingress | Expose HTTP/HTTPS ra ngoài, routing theo host/path |
ConfigMap / Secret | Inject config/secret vào Pod |
PersistentVolume / PVC | Storage có lifecycle riêng với Pod |
Namespace | Phân vùng logic cho object trong cluster |
Namespace là cơ chế chia cluster thành nhiều virtual cluster. Default cluster có sẵn:
default — nơi object được tạo nếu không khai báo namespace.
kube-system — chứa các component của K8s (CoreDNS, kube-proxy DaemonSet…).
kube-public — readable bởi mọi người, dùng cho cluster info.
kube-node-lease — chứa Lease object cho node heartbeat.
Bạn nên tạo namespace riêng cho team/project — không nên nhét hết vào default.
kubectl là command-line tool chính thức để giao tiếp với API Server. Cú pháp cơ bản:
kubectl [command] [TYPE] [NAME] [flags]
Ví dụ:
# Xem các node
kubectl get nodes
# Xem pod trong namespace default
kubectl get pods
# Xem pod trong tất cả namespace
kubectl get pods -A
# Mô tả chi tiết pod
kubectl describe pod nginx-abc123
# Xem log
kubectl logs nginx-abc123
kubectl logs -f nginx-abc123 # follow
kubectl logs nginx-abc123 -c sidecar # container cụ thể
# Exec vào container
kubectl exec -it nginx-abc123 -- /bin/sh
# Apply YAML
kubectl apply -f deployment.yaml
# Xoá object
kubectl delete -f deployment.yaml
kubectl delete pod nginx-abc123
# Edit object đang chạy
kubectl edit deployment nginx
Hãy ghi nhớ phân biệt:
kubectl apply -f — declarative, idempotent, khuyến nghị cho mọi production workflow.
kubectl create — imperative, chạy lần đầu OK nhưng chạy lần hai sẽ báo already exists.
kubectl run, kubectl expose — imperative shortcut, tốt để học, không nên dùng trong production.
kubectl apply đến container chạyHiểu được luồng này là aha moment với K8s. Giả sử bạn chạy:
kubectl apply -f nginx-deployment.yaml
Điều gì xảy ra phía sau?
kubectl đọc file YAML, validate cơ bản, gửi HTTPS POST/PUT đến API Server.
API Server xác thực (authentication), kiểm tra quyền (authorization qua RBAC), chạy admission controllers (validation, mutation), rồi persist object vào etcd.
Deployment controller (chạy trong controller-manager) đang watch các Deployment, thấy có Deployment mới → tạo ReplicaSet tương ứng.
ReplicaSet controller đang watch ReplicaSet, thấy ReplicaSet cần N pod → tạo N Pod object với nodeName rỗng.
kube-scheduler đang watch các Pod chưa có node → chọn node phù hợp → ghi nodeName vào Pod object.
kubelet trên node đó đang watch Pod gán cho mình → gọi container runtime (qua CRI) để pull image, tạo network namespace, tạo container, start.
kubelet liên tục report status pod (Running/Ready/etc.) lên API Server → ghi vào etcd.
Nếu pod thuộc Service, EndpointSlice controller cập nhật endpoint, kube-proxy trên mọi node refresh network rules để traffic Service → đến đúng pod.
Toàn bộ luồng này là asynchronous và dựa trên cơ chế watch: mỗi component subscribe sự kiện từ API Server, không có ai gọi nhau trực tiếp. Đó là lý do K8s rất resilient — bạn có thể restart từng component mà cluster vẫn hoạt động.
K8s không liên kết object bằng foreign key. Thay vào đó, mọi liên kết được thực hiện qua label selector.
Ví dụ Service nối với Pod:
# Pod có label app=nginx
apiVersion: v1
kind: Pod
metadata:
name: nginx-1
labels:
app: nginx
tier: frontend
spec:
containers: [...]
---
# Service chọn pod bằng selector
apiVersion: v1
kind: Service
metadata:
name: nginx-svc
spec:
selector:
app: nginx # matches mọi pod có label app=nginx
ports:
- port: 80
targetPort: 80
Tính chất này có hai hệ quả lớn:
Bạn thay pod mà không cần update Service — pod mới chỉ cần label đúng.
Bạn có thể làm canary release bằng cách thêm label đặc biệt cho 1 pod và đổi selector tạm thời.
| Tiêu chí | Docker Compose | Docker Swarm | Nomad | Kubernetes |
|---|---|---|---|---|
| Độ phức tạp | Rất thấp | Thấp | Trung bình | Cao |
| Multi-node | Không | Có | Có | Có |
| Tự healing | Không | Cơ bản | Đầy đủ | Đầy đủ |
| Autoscaling | Không | Không | Plugin | HPA/VPA/CA |
| Ecosystem | Nhỏ | Hẹp, đang teo | Trung bình | Khổng lồ (CNCF) |
| Khi nên dùng | Dev local, demo | App nhỏ, đội nhỏ | Mix VM + container | App lớn, microservices, multi-cluster |
K8s không phải silver bullet. Nếu bạn chỉ có vài service đơn giản, Docker Compose hay Swarm có thể đủ — và rẻ hơn nhiều về vận hành.
Cluster — tập hợp control plane + nodes.
Node — một máy (VM hoặc physical) trong cluster.
Pod — đơn vị triển khai nhỏ nhất, 1+ container chia chung network namespace.
Workload — app chạy trên K8s, gồm 1 hoặc nhiều Pod được quản lý bởi controller (Deployment, StatefulSet…).
Namespace — phân vùng logic.
Object — bản ghi persistent trong etcd, mô tả intent (desired state).
Controller — control loop đưa current state → desired state.
Manifest — file YAML/JSON khai báo object.
Resource — endpoint trong API (vd. pods, services) — không nhầm với CPU/memory resource.
CRD — Custom Resource Definition, cách mở rộng API với object riêng.
Operator — pattern: CRD + controller, quản lý app phức tạp (Postgres, Kafka…).
Trong phần này bạn đã nắm được:
Vì sao Kubernetes ra đời và nó giải quyết vấn đề gì.
Kiến trúc cluster: control plane (API server, etcd, scheduler, controller-manager) + worker node (kubelet, kube-proxy, runtime).
Mô hình declarative — bạn khai báo intent, K8s lo phần thực thi.
Cách kubectl tương tác với cluster.
Vòng đời một request từ kubectl apply đến container thực sự chạy.
Cơ chế label selector để liên kết object.
Trong Phần 2, ta sẽ dựng cluster đầu tiên bằng minikube và kind cho local, rồi kubeadm cho production.
Phần 2: Cài đặt cluster: minikube, kind, kubeadm và kubectl →