Проблема
Сканер контейнеров и cluster posture может честно показывать опасные privileged pods, hostPath mounts или небезопасные capabilities, но если admission policy их не блокирует, drift быстро возвращается.
Часто security review заканчивается единичным отчётом без встраивания в CI/CD и cluster governance. Через неделю новый chart или override values file приносит те же проблемы обратно.
Решение
Нужно разделить три уровня: posture visibility, preventive policy и runtime observation. Первый отвечает за инвентаризацию, второй - за запрет известного плохого состояния, третий - за сигнал на уже запущенные аномалии.
Полезно хранить hardening как diff: non-root, readOnlyRootFilesystem, dropped capabilities, network policy, namespace isolation, image provenance. Тогда исправление превращается не в спор, а в набор конкретных controls.
Что проверить руками
- Проверить, как cluster scan findings соотносятся с admission policy и runtime alerts.
- Выделить несколько class-of-risk: privileged, hostPath, writable root fs, broad RBAC, image trust, exposed dashboard.
- Проверить, не живут ли исключения только в values override без срока действия и владельца.
- Согласовать, какие misconfigurations должны быть block, warn или monitor.
Типичные ошибки
- Считать posture-report завершённой защитой.
- Блокировать всё одинаково, без перехода через warn/monitor и без понятного исключения.
- Не связывать namespace/business context с risk appetite.
Defensive checklist
- Есть соответствие posture finding -> policy decision -> runtime verification.
- Критичные misconfigurations имеют preventive control.
- Исключения ограничены сроком, владельцем и причиной.
- Retest повторяет deploy path, а не только ручной scan.
Безопасный пример кода
Gatekeeper constraint для запрета privileged containers. Пример рассчитан на owned/lab-среду и показывает инженерную логику проверки, а не эксплуатационную цепочку.
apiVersion: constraints.gatekeeper.sh/v1beta1
kind: K8sPSPPrivilegedContainer
metadata:
name: disallow-privileged
spec:
match:
kinds:
- apiGroups: [""]
kinds: ["Pod"]
excludedNamespaces:
- kube-system
parameters:
exemptImages:
- "registry.example/trusted-debug:*"
Как это должно попасть в отчёт
- Cluster layer map: posture, admission, runtime, owner, exception path.
- Evidence: offending manifest, namespace, control gap, recommended policy diff.
- Retest: hardened manifest deploys, insecure one is denied or flagged as designed.