Kubernetes изглежда елегантен в уроците, но production средата разказва различна история. Ето 15 реални сценария, които разделят начинаещите оператори от закалените в битки инженери — с приложими решения за всеки от тях.

⚔️ Задълбочено дебъгване

1. Pod заседнал в CrashLoopBackOff, без логове, без грешки

Как дебъгвате отвъд kubectl logs и describe?

  • Проверете логовете на предишния контейнер: kubectl logs <pod> --previous - контейнерът може да се срине преди да запише логове
  • Влезте в контейнера с дебъг шел: kubectl debug -it <pod> --image=busybox --target=<container>
  • Инспектирайте събития на ниво node: kubectl get events --field-selector involvedObject.name=<pod>
  • Проверете init контейнерите: Често виновникът е failing init контейнер, който се изпълнява преди основния контейнер
  • Прегледайте entrypoint на контейнера: Процесът може да излезе веднага — тествайте образа локално с docker run -it <image> sh
  • Проверете ресурсните лимити: OOMKilled контейнерите не винаги оставят логове — проверете kubectl describe pod за Last State: OOMKilled

2. StatefulSet pod не се свързва отново с PVC след срив на node

Как възстановявате без пресъздаване на storage?

  • Проверете PV статуса: kubectl get pv - търсете Released или Failed състояние
  • Принудително изтрийте заседналия pod: kubectl delete pod <pod> --force --grace-period=0
  • Проверете VolumeAttachment обектите: kubectl get volumeattachments - остарелите attachments могат да блокират повторното свързване
  • Изтрийте остарелия VolumeAttachment: kubectl delete volumeattachment <name>
  • Проверете здравето на CSI драйвера: Проверете CSI драйвер pod-овете в kube-system namespace
  • Последна опция - patch на PV: Премахнете claimRef за да позволите повторно свързване: kubectl patch pv <pv-name> -p '{"spec":{"claimRef": null}}'

3. Pod-овете са Pending, Cluster Autoscaler не мащабира нагоре

Топ 3 стъпки за дебъгване:

  • Стъпка 1 - Проверете логовете на Autoscaler: kubectl logs -n kube-system -l app=cluster-autoscaler - търсете "scale up" решения и защо са отхвърлени
  • Стъпка 2 - Проверете ограниченията на node group: Проверете дали е достигнат лимитът за максимални nodes, дали необходимият тип инстанция е наличен във вашия регион и дали има достатъчно IAM права
  • Стъпка 3 - Изследвайте изискванията за планиране на pod: Проверете за nodeSelector, affinity правила или taints, които никоя node група не може да удовлетвори. Изпълнете kubectl describe pod и погледнете секцията Events за грешки при планиране
  • Чести виновници: PodDisruptionBudget блокиращ scale-down (което блокира scale-up цикли), pod-ове с локално хранилище, които не могат да бъдат препланирани, и недостатъчна квота при облачния доставчик

4. NetworkPolicy блокира трафик между namespaces

Как проектирате правила с минимални привилегии и ги тествате безопасно?

  • Започнете с audit режим: Използвайте инструменти като Cilium's policy audit режим, за да видите какво ще бъде блокирано преди прилагане
  • Дизайн модел - Default deny + explicit allow:
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default-deny-all
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress
  • Разрешете трафик между namespaces изрично:
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-from-frontend
  namespace: backend
spec:
  podSelector:
    matchLabels:
      app: api
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          name: frontend
      podSelector:
        matchLabels:
          app: web
  • Безопасно тестване: Деплойнете debug pod и използвайте nc -zv <service> <port> за да тествате свързаност преди и след промени в политиката
  • Използвайте визуализация на политики: Инструменти като Cilium Hubble или Calico's policy board помагат за визуализиране на трафик потоците

5. Услуга трябва да се свърже с външна DB чрез VPN вътре в клъстера

Как архитектурирате за HA + сигурност?

  • Опция 1 - Sidecar VPN контейнер: Стартирайте VPN клиент като sidecar в pod-ове, които имат нужда от DB достъп. Добре за изолация, но дублира връзки.
  • Опция 2 - Специализирани VPN gateway pod-ове: Деплойнете DaemonSet или Deployment на VPN gateway pod-ове със Service. Насочете трафика през тези gateways използвайки NetworkPolicy.
  • Опция 3 - VPN на ниво node (препоръчително за HA):
# Използвайте DaemonSet с hostNetwork: true
apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: vpn-gateway
spec:
  selector:
    matchLabels:
      app: vpn-gateway
  template:
    spec:
      hostNetwork: true
      containers:
      - name: vpn
        image: your-vpn-image
        securityContext:
          capabilities:
            add: ["NET_ADMIN"]
  • Съображения за сигурност: Използвайте Kubernetes Secrets за VPN credentials, имплементирайте NetworkPolicy за ограничаване на pod-ове, които могат да достигнат VPN gateway, активирайте mTLS ако се поддържа от вашето VPN решение
  • HA архитектура: Стартирайте множество VPN pod-ове в различни availability zones, използвайте headless Service с client-side load balancing, имплементирайте health checks, които проверяват действителна DB свързаност

🧱 Сигурност + Архитектура

6. Управление на multi-tenant EKS клъстер

Как изолирате workloads с RBAC, квоти и мрежова сегментация?

  • Namespace изолация: Един namespace за tenant със стриктен RBAC
# Role ограничена до tenant namespace
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  namespace: tenant-a
  name: tenant-role
rules:
- apiGroups: ["", "apps"]
  resources: ["pods", "deployments", "services"]
  verbs: ["get", "list", "create", "update", "delete"]
  • Ресурсни квоти за tenant:
apiVersion: v1
kind: ResourceQuota
metadata:
  name: tenant-quota
  namespace: tenant-a
spec:
  hard:
    requests.cpu: "10"
    requests.memory: 20Gi
    limits.cpu: "20"
    limits.memory: 40Gi
    pods: "50"
  • Мрежова сегментация: Default-deny NetworkPolicy за namespace, explicit allow правила само за необходима cross-tenant комуникация
  • Допълнително укрепване: Използвайте PodSecurityAdmission за прилагане на restricted политики, имплементирайте OPA/Gatekeeper за custom политики, разгледайте специализирани node pools за tenant при чувствителни workloads

7. Kubelet продължава да се рестартира на един node

Къде поглеждате първо – systemd, container runtime или cgroups?

  • Стъпка 1 - Проверете systemd статуса: systemctl status kubelet и journalctl -u kubelet -f
  • Стъпка 2 - Търсете OOM kills: dmesg | grep -i "oom\|killed" - kubelet може да бъде OOM killed
  • Стъпка 3 - Проверете container runtime: systemctl status containerd (или docker), след това crictl ps за да проверите дали runtime отговаря
  • Стъпка 4 - Проверете cgroup конфигурацията: Уверете се, че cgroup driver съвпада между kubelet и container runtime (и двата трябва да използват systemd или cgroupfs)
  • Стъпка 5 - Disk pressure: df -h на /var/lib/kubelet и /var/lib/containerd
  • Чести причини: Изтекли сертификати, проблеми със свързаността към API server, повредено kubelet състояние (опитайте да премахнете /var/lib/kubelet/cpu_manager_state)

8. Критичен pod е евиктиран поради node pressure

Обяснете QoS класове и политики за евикция:

  • QoS класове (ред на евикция):
  • BestEffort (евиктират се първи): Няма зададени requests или limits
  • Burstable (евиктират се втори): Requests < Limits, или само някои контейнери имат limits
  • Guaranteed (евиктират се последни): Requests = Limits за ВСИЧКИ контейнери
# Guaranteed QoS пример
resources:
  requests:
    memory: "1Gi"
    cpu: "500m"
  limits:
    memory: "1Gi"
    cpu: "500m"
  • Защитете критични pod-ове: Използвайте PriorityClass с preemptionPolicy: Never или висока стойност на priority
apiVersion: scheduling.k8s.io/v1
kind: PriorityClass
metadata:
  name: critical-workload
value: 1000000
globalDefault: false
preemptionPolicy: PreemptLowerPriority
description: "Критични workloads, които не трябва да бъдат евиктирани"
  • Прагове за евикция: Конфигурирайте kubelet флагове като --eviction-hard и --eviction-soft за задаване на прагове за memory/disk pressure

9. Rolling update причини downtime

Какво се обърка в readiness/startup probe или deployment конфигурацията?

  • Чести виновници:
  • Липсваща readiness probe: Трафикът се насочва преди приложението да е готово
  • Агресивни probe настройки: initialDelaySeconds твърде кратък за бавно стартиращи приложения
  • Грешен endpoint: Probe удря тежък endpoint, който timeout-ва
# Правилна probe конфигурация
readinessProbe:
  httpGet:
    path: /health/ready
    port: 8080
  initialDelaySeconds: 10
  periodSeconds: 5
  failureThreshold: 3
startupProbe:  # За бавно стартиращи приложения
  httpGet:
    path: /health/started
    port: 8080
  failureThreshold: 30
  periodSeconds: 10
  • Deployment настройки за преглед:
spec:
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxUnavailable: 0      # Никога не премахвайте здрави pod-ове
      maxSurge: 1            # Добавяйте по един нов pod
  minReadySeconds: 30        # Изчакайте преди маркиране като available
  • Не забравяйте preStop hooks: Позволете graceful shutdown преди SIGTERM
lifecycle:
  preStop:
    exec:
      command: ["/bin/sh", "-c", "sleep 15"]

10. Ingress Controller се проваля под натоварване

Как дебъгвате и мащабирате routing ефективно?

  • Стъпки за дебъгване:
  • Проверете логовете на контролера: kubectl logs -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx
  • Мониторирайте connection метрики: Търсете nginx_ingress_controller_nginx_process_connections
  • Проверете за config reload бури: Честите Ingress промени причиняват reloads
  • Стратегии за мащабиране:
  • Хоризонтално мащабиране: Увеличете replicas и използвайте pod anti-affinity за дистрибуция
  • Настройте worker processes: Задайте worker-processes: "auto" в ConfigMap
  • Активирайте keep-alive: Намалете connection overhead с upstream keep-alive
# Ingress ConfigMap настройки
data:
  worker-processes: "auto"
  max-worker-connections: "65536"
  upstream-keepalive-connections: "200"
  keep-alive: "75"
  • Обмислете разделяне: Използвайте отделни Ingress контролери за различни класове трафик (вътрешен срещу външен)

⚙️ Производителност + Надеждност

11. Istio sidecar консумира повече CPU от вашето приложение

Как профилирате и оптимизирате mesh производителността?

  • Първо профилирайте: Използвайте istioctl proxy-config за инспекция на Envoy конфигурацията
  • Проверете размера на конфигурацията: istioctl proxy-status показва статуса на config sync
  • Стратегии за оптимизация:
  • Ограничете sidecar обхвата:
apiVersion: networking.istio.io/v1beta1
kind: Sidecar
metadata:
  name: default
  namespace: my-app
spec:
  egress:
  - hosts:
    - "./*"                    # Само локален namespace
    - "istio-system/*"         # Control plane
  • Настройте ресурсни лимити:
# В IstioOperator
spec:
  values:
    global:
      proxy:
        resources:
          requests:
            cpu: 50m
            memory: 128Mi
          limits:
            cpu: 200m
            memory: 256Mi
  • Деактивирайте ненужни функции: Изключете access logging, намалете tracing sampling rate
  • Обмислете sidecar-less: Istio ambient mesh премахва sidecars за L4 трафик

12. etcd забавя операциите на control plane

Основни причини + как го настройвате безопасно?

  • Чести основни причини:
  • Disk I/O латентност (etcd е много чувствителен към производителността на диска)
  • Твърде много обекти (secrets, configmaps, events)
  • Мрежова латентност между etcd членове
  • Големи размери на обекти (secrets с големи данни)
  • Диагностика:
# Проверете etcd метрики
etcdctl endpoint status --write-out=table
etcdctl endpoint health

# Ключови метрики за наблюдение
- etcd_disk_wal_fsync_duration_seconds (трябва да е < 10ms)
- etcd_disk_backend_commit_duration_seconds
- etcd_server_slow_apply_total
  • Безопасна настройка:
  • Използвайте SSD/NVMe хранилище (IOPS > 3000, латентност < 1ms)
  • Увеличете --quota-backend-bytes ако достигате space quota
  • Активирайте auto-compaction: --auto-compaction-retention=1
  • Редовна дефрагментация (по време на maintenance прозорци)
  • Намалете event TTL за ограничаване на натрупването на събития

13. Трябва да наложите образи само от доверен вътрешен registry

Gatekeeper, Kyverno или custom Admission Webhook – какъв е вашият ход?

  • Препоръка: Kyverno за простота, Gatekeeper за сложни политики
  • Kyverno подход (по-прост):
apiVersion: kyverno.io/v1
kind: ClusterPolicy
metadata:
  name: restrict-image-registries
spec:
  validationFailureAction: Enforce
  rules:
  - name: validate-registries
    match:
      any:
      - resources:
          kinds:
          - Pod
    validate:
      message: "Образите трябва да идват от вътрешния registry"
      pattern:
        spec:
          containers:
          - image: "registry.internal.com/*"
          initContainers:
          - image: "registry.internal.com/*"
  • Gatekeeper подход (по-гъвкав):
apiVersion: constraints.gatekeeper.sh/v1beta1
kind: K8sAllowedRepos
metadata:
  name: repo-is-internal
spec:
  match:
    kinds:
    - apiGroups: [""]
      kinds: ["Pod"]
  parameters:
    repos:
    - "registry.internal.com/"
  • Custom webhook: Само ако имате нужда от интеграция с външни системи или custom логика, която policy engines не могат да обработят
  • Професионален съвет: Също имплементирайте верификация на image signatures с Cosign + Kyverno за supply chain сигурност

14. Pod-ове заседнали в ContainerCreating завинаги

CNI attach забавяне? OverlayFS корупция? Разкажете процеса си за намиране на основната причина:

  • Стъпка 1 - Describe на pod: kubectl describe pod <pod> - проверете секцията Events за специфични грешки
  • Стъпка 2 - Проверете CNI:
# Проверете CNI plugin pod-ове
kubectl get pods -n kube-system -l k8s-app=calico-node  # или вашия CNI

# Проверете CNI логове
kubectl logs -n kube-system -l k8s-app=calico-node

# Проверете дали CNI config съществува
ls /etc/cni/net.d/
  • Стъпка 3 - Проверете container runtime:
# Containerd
crictl ps
crictl logs <container-id>
journalctl -u containerd

# Проверете за заседнали sandbox контейнери
crictl pods | grep NotReady
  • Стъпка 4 - Проверете storage:
# Overlay filesystem проблеми
df -h /var/lib/containerd
mount | grep overlay

# Почистете ако е повреден
crictl rmi --prune
  • Стъпка 5 - Проверете за изчерпване на ресурси: IP адреси изчерпани в CNI subnet, твърде много pod-ове на node, достигнат лимит на inotify watch

15. Случайни DNS грешки в Pod-ове

Как дебъгвате CoreDNS, kube-proxy и conntrack взаимодействия?

  • Стъпка 1 - Тествайте DNS от pod:
kubectl run -it --rm debug --image=busybox -- nslookup kubernetes
kubectl run -it --rm debug --image=busybox -- nslookup google.com
  • Стъпка 2 - Проверете CoreDNS:
# CoreDNS pod статус
kubectl get pods -n kube-system -l k8s-app=kube-dns

# CoreDNS логове
kubectl logs -n kube-system -l k8s-app=kube-dns

# Проверете CoreDNS метрики
kubectl top pods -n kube-system -l k8s-app=kube-dns
  • Стъпка 3 - Проверете kube-proxy:
# Проверете kube-proxy mode
kubectl get cm -n kube-system kube-proxy -o yaml | grep mode

# Проверете iptables/ipvs правила
iptables -t nat -L | grep coredns
ipvsadm -ln | grep <coredns-ip>
  • Стъпка 4 - Conntrack проблеми (чест виновник):
# Проверете conntrack таблица
conntrack -S
cat /proc/sys/net/netfilter/nf_conntrack_count
cat /proc/sys/net/netfilter/nf_conntrack_max

# Увеличете ако достигате лимити
sysctl -w net.netfilter.nf_conntrack_max=524288
  • Стъпка 5 - Поправката за race condition: Добавете към pod spec за избягване на UDP source port изчерпване:
dnsConfig:
  options:
  - name: single-request-reopen
  - name: ndots
    value: "2"
  • Професионален съвет: Използвайте NodeLocal DNSCache за намаляване на CoreDNS натоварването и избягване на conntrack проблеми за DNS трафик

Обобщение

Тези 15 сценария представят реалността на работата с Kubernetes в production. Ключовите изводи:

  • Винаги първо събирайте данни: Events, логове, метрики и node статус преди да правите промени
  • Наслоявайте защитите: RBAC + NetworkPolicy + Resource Quotas + Pod Security
  • Проектирайте за отказ: Правилни QoS класове, priority classes и PodDisruptionBudgets
  • Мониторирайте control plane: Здравето на etcd и kubelet е критично
  • Тествайте преди прилагане: Audit режим за политики, canary deployments за промени

Production Kubernetes изисква систематичен подход за дебъгване и задълбочено разбиране на основните компоненти. Овладейте тези сценарии и ще бъдете готови за каквото и да ви поднесат вашите клъстери.