Sau bài này bạn làm được: đọc/sửa Helm chart của team; dùng Kustomize overlay cho multi-env; hiểu RBAC đủ để đọc manifest platform; biết Pod Security Standards thay PSP.


Helm — package manager cho Kubernetes

Vấn đề

20 YAML files × 3 environments (dev/staging/prod) = 60 files gần giống nhau. Helm giải quyết bằng templating + packaging.

Chart structure

my-app/
├── Chart.yaml              # Metadata (name, version, appVersion)
├── values.yaml             # Default values
├── templates/
│   ├── deployment.yaml     # Template với {{ .Values.xxx }}
│   ├── service.yaml
│   ├── ingress.yaml
│   ├── configmap.yaml
│   ├── _helpers.tpl        # Template helpers
│   └── NOTES.txt           # Post-install message
└── charts/                 # Dependencies (sub-charts)

Template example

# templates/deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: {{ include "my-app.fullname" . }}
spec:
  replicas: {{ .Values.replicaCount }}
  template:
    spec:
      containers:
      - name: {{ .Chart.Name }}
        image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
        resources:
          {{- toYaml .Values.resources | nindent 10 }}
# values.yaml
replicaCount: 3
image:
  repository: my-app
  tag: "1.2.0"
resources:
  requests:
    cpu: "100m"
    memory: "128Mi"
  limits:
    memory: "256Mi"

Helm commands

# Thêm repo
helm repo add bitnami https://charts.bitnami.com/bitnami
helm repo update

# Tìm chart
helm search repo nginx

# Cài chart
helm install my-release bitnami/nginx -n production

# Override values
helm install my-release ./my-app -f values-prod.yaml
helm install my-release ./my-app --set replicaCount=5

# Xem rendered YAML (dry-run)
helm template my-release ./my-app -f values-prod.yaml

# Upgrade
helm upgrade my-release ./my-app -f values-prod.yaml

# Rollback
helm rollback my-release 1    # Revision 1

# Xem history
helm history my-release

# Uninstall
helm uninstall my-release

# List releases
helm list -A

Helm release

Mỗi lần helm install/upgrade tạo một release — snapshot trạng thái (revision). Rollback quay về revision trước.

helm history my-release
# REVISION  STATUS      DESCRIPTION
# 1         superseded  Install complete
# 2         deployed    Upgrade complete

Kustomize — overlay without template

Khác Helm thế nào

HelmKustomize
ApproachTemplate (Go template)Overlay (patch YAML gốc)
Learning curvePhức tạp (template syntax)Đơn giản (chỉ YAML)
Package/shareChart package + repoThư mục + URL
Built-in kubectlKhông (cần cài Helm)kubectl apply -k
StateRelease historyKhông (stateless)

Structure

base/
├── kustomization.yaml
├── deployment.yaml
├── service.yaml
└── configmap.yaml

overlays/
├── dev/
│   ├── kustomization.yaml
│   └── patch-replicas.yaml
├── staging/
│   └── kustomization.yaml
└── prod/
    ├── kustomization.yaml
    ├── patch-replicas.yaml
    └── patch-resources.yaml

Base kustomization

# base/kustomization.yaml
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- deployment.yaml
- service.yaml
- configmap.yaml
commonLabels:
  app: my-api

Overlay

# overlays/prod/kustomization.yaml
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../base
namespace: production
namePrefix: prod-
patches:
- path: patch-replicas.yaml
configMapGenerator:
- name: app-config
  literals:
  - LOG_LEVEL=warn
  - DB_HOST=prod-db.internal
# overlays/prod/patch-replicas.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-api
spec:
  replicas: 5

Commands

# Preview
kubectl kustomize overlays/prod/

# Apply
kubectl apply -k overlays/prod/

# Diff
kubectl diff -k overlays/prod/

Khi nào Helm, khi nào Kustomize

ScenarioRecommendation
Cài third-party app (nginx, cert-manager, Prometheus)Helm (chart có sẵn)
App nội bộ, multi-env (dev/staging/prod)Kustomize (đơn giản, no template)
Cần versioning + rollbackHelm (release history)
Team nhỏ, muốn tối giảnKustomize
Kết hợp: Helm render → Kustomize patchHelm template + Kustomize overlay

RBAC — Role-Based Access Control

Mô hình

[User/ServiceAccount] ── RoleBinding ── [Role]
                                    rules: [resources, verbs]

Role (namespace-scoped)

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: pod-reader
  namespace: production
rules:
- apiGroups: [""]                    # Core API group
  resources: ["pods", "pods/log"]
  verbs: ["get", "list", "watch"]
- apiGroups: ["apps"]
  resources: ["deployments"]
  verbs: ["get", "list"]

ClusterRole (cluster-scoped)

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: namespace-admin
rules:
- apiGroups: ["", "apps", "batch"]
  resources: ["*"]
  verbs: ["*"]
- apiGroups: [""]
  resources: ["secrets"]
  verbs: ["get", "list"]              # Giới hạn secret access

RoleBinding / ClusterRoleBinding

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: dev-pod-reader
  namespace: production
subjects:
- kind: User
  name: [email protected]
  apiGroup: rbac.authorization.k8s.io
- kind: ServiceAccount
  name: ci-bot
  namespace: ci
roleRef:
  kind: Role
  name: pod-reader
  apiGroup: rbac.authorization.k8s.io

ServiceAccount

Mỗi pod chạy với một ServiceAccount (mặc định: default). Token mount tại /var/run/secrets/kubernetes.io/serviceaccount/.

apiVersion: v1
kind: ServiceAccount
metadata:
  name: my-app-sa
  namespace: production
---
# Pod dùng ServiceAccount
spec:
  serviceAccountName: my-app-sa
  automountServiceAccountToken: false    # Không cần API access → tắt

Kiểm tra quyền

# Kiểm tra user hiện tại có quyền gì
kubectl auth can-i get pods -n production
kubectl auth can-i delete deployments -n production

# Kiểm tra cho ServiceAccount
kubectl auth can-i get pods -n production --as=system:serviceaccount:production:my-app-sa

# Liệt kê tất cả RoleBinding
kubectl get rolebinding -n production
kubectl get clusterrolebinding

Pod Security Standards

Thay thế PodSecurityPolicy (deprecated K8s 1.21, removed 1.25).

Ba cấp độ

LevelCho phépDùng cho
PrivilegedKhông giới hạnInfra system (kube-system)
BaselineChặn các cấu hình nguy hiểm nhấtHầu hết workload
RestrictedChặn tối đa, enforce best practiceWorkload nhạy cảm

Enforce bằng PodSecurity admission

apiVersion: v1
kind: Namespace
metadata:
  name: production
  labels:
    pod-security.kubernetes.io/enforce: restricted
    pod-security.kubernetes.io/warn: restricted
    pod-security.kubernetes.io/audit: restricted
  • enforce: block pod vi phạm.
  • warn: cho tạo nhưng hiện warning.
  • audit: ghi vào audit log.

Restricted level yêu cầu

# Pod phải:
spec:
  securityContext:
    runAsNonRoot: true
    seccompProfile:
      type: RuntimeDefault
  containers:
  - name: app
    securityContext:
      allowPrivilegeEscalation: false
      capabilities:
        drop: ["ALL"]
      readOnlyRootFilesystem: true    # Recommended

Bản đồ mở rộng — đọc tiếp ở đâu

GitOps: Argo CD / Flux

Sync cluster state từ Git repo. Thay kubectl apply trong CI bằng pull-based deployment:

  • Argo CD: UI dashboard, multi-cluster, ApplicationSet.
  • Flux: lightweight, GitOps Toolkit, native Kustomize integration.

Nối với Mạng bài 15 — IaC và GitOps.

Service mesh: Istio / Linkerd

East-west traffic management, mTLS, observability. Nối với Mạng bài 17 — Service mesh và mTLS.

Policy engine: OPA Gatekeeper / Kyverno

Admission control: chặn image không signed, yêu cầu label, enforce resource limits. Guardrail cho manifest.

Multi-cluster

Federation, Liqo, Admiralty — khi một cluster không đủ. Phức tạp, chỉ khi thực sự cần.

eBPF / Cilium

Thay kube-proxy, L7 network policy, kernel-level observability (Hubble). Xu hướng CNI 2025-2026.


Tóm tắt

  • Helm: template + packaging. Dùng cho third-party chart và app cần versioning.
  • Kustomize: overlay YAML, built-in kubectl. Dùng cho app nội bộ multi-env.
  • RBAC: Role → RoleBinding → User/ServiceAccount. Tắt automountServiceAccountToken khi không cần.
  • Pod Security Standards: Privileged / Baseline / Restricted. Enforce qua namespace label.
  • Đọc tiếp: GitOps (Argo/Flux), Service mesh (Istio/Linkerd), Policy (Gatekeeper/Kyverno).

Câu hỏi hay gặp

Helm values quá phức tạp, có cách nào đơn giản hơn?

Trả lời: Dùng helm template render ra plain YAML → apply bằng kubectl apply hoặc pipe qua Kustomize. Hoặc chỉ dùng Kustomize nếu không cần chart ecosystem.

RBAC rules: resources: ["*"] có nên dùng?

Trả lời: Không cho production. Wildcard cho full access tới mọi resource — vi phạm principle of least privilege. Liệt kê cụ thể resources cần thiết. Dùng kubectl auth can-i --list để review quyền hiện tại.

Pod Security Standards có thay thế hoàn toàn OPA/Kyverno không?

Trả lời: Không. Pod Security chỉ kiểm tra pod spec (security context). OPA/Kyverno kiểm tra bất kỳ resource nào: enforce label convention, chặn image không trusted, yêu cầu resource limits, validate Ingress config… Hai layer bổ sung nhau.


Đây là bài cuối cùng trong loạt Kubernetes cho Developer. Quay lại mục lục để chọn lộ trình đọc theo mục tiêu, hoặc khám phá các loạt liên quan: Mạng & DevOps, Linux thực dụng.