La configuration par défaut de Kubernetes est conçue pour faciliter le démarrage, pas pour la sécurité en production. Après avoir audité une douzaine de clusters dans les secteurs finance, télécoms et SaaS, les mêmes lacunes apparaissent dans presque tous. Cet article couvre les contrôles avec le meilleur ratio impact/effort, ceux que vous pouvez implémenter cette semaine.
Le Modèle de Menace
Avant de durcir quoi que ce soit, soyez clair sur ce que vous défendez :
- Charge de travail compromise - un conteneur est pénétré via une vulnérabilité dans l’application ou ses dépendances. Peut-il atteindre l’API Server ? Peut-il se déplacer latéralement vers d’autres pods ?
- Threat interne - un développeur ou un pipeline CI obtient plus d’accès que nécessaire. Peut-il lire les secrets des autres namespaces ?
- Image malveillante - une image compromise est déployée dans votre cluster. S’exécute-t-elle avec des privilèges root ? Peut-elle modifier les binaires du système hôte ?
Chaque contrôle ci-dessous adresse au moins un de ces scénarios.
Contrôle 1 : RBAC - Moindre Privilège Réel
L’erreur la plus fréquente que j’observe : accorder ClusterAdmin à des comptes de service parce que c’est “plus simple”. Ce n’est pas plus simple. C’est une bombe à retardement.
Ce que j’ai trouvé dans un audit récent :
kubectl get clusterrolebindings -o json | \ jq '.items[] | select(.roleRef.name == "cluster-admin") | .subjects[]'Résultat : 14 comptes de service avec des droits cluster-admin dans un cluster de 200 nœuds. Dont l’opérateur de monitoring et le runner CI.
La règle : créez des rôles avec uniquement les verbes et ressources nécessaires.
apiVersion: rbac.authorization.k8s.io/v1kind: Rolemetadata: name: deploy-only namespace: productionrules:- apiGroups: ["apps"] resources: ["deployments"] verbs: ["get", "list", "patch", "update"]Contrôle 2 : Network Policies - Segmentation par Défaut
Par défaut, chaque pod peut communiquer avec chaque autre pod dans le cluster. C’est catastrophique pour la sécurité.
Commencez par une politique de refus global, puis autorisez explicitement :
# Default deny all ingress and egress in a namespaceapiVersion: networking.k8s.io/v1kind: NetworkPolicymetadata: name: default-deny-all namespace: productionspec: podSelector: {} policyTypes: - Ingress - EgressPuis autorisez uniquement ce qui est nécessaire :
apiVersion: networking.k8s.io/v1kind: NetworkPolicymetadata: name: allow-frontend-to-api namespace: productionspec: podSelector: matchLabels: app: api ingress: - from: - podSelector: matchLabels: app: frontend ports: - port: 8080Contrôle 3 : Pod Security Standards
Depuis Kubernetes 1.25, les Pod Security Standards remplacent les PodSecurityPolicies dépréciées. Configurez-les au niveau namespace :
apiVersion: v1kind: Namespacemetadata: name: production labels: pod-security.kubernetes.io/enforce: restricted pod-security.kubernetes.io/audit: restricted pod-security.kubernetes.io/warn: restrictedLe profil restricted interdit :
- Les conteneurs s’exécutant en root
- L’escalade de privilèges
- Les capacités Linux dangereuses
- Le montage des chemins sensibles de l’hôte
Pour les applications legacy qui nécessitent root, utilisez le profil baseline et documentez explicitement pourquoi.
Contrôle 4 : Secrets Management - Sortir d’etcd
Les secrets Kubernetes sont encodés en base64, pas chiffrés. N’importe qui ayant accès à etcd peut les lire. N’importe qui pouvant exec dans un pod peut lire les secrets montés.
L’approche que nous recommandons :
- Chiffrement au repos d’etcd (configurer
EncryptionConfiguration) - Intégration avec un gestionnaire de secrets externe (HashiCorp Vault ou AWS Secrets Manager)
- Rotation automatique via l’opérateur External Secrets
apiVersion: external-secrets.io/v1beta1kind: ExternalSecretmetadata: name: db-credentialsspec: refreshInterval: 1h secretStoreRef: name: vault-backend kind: ClusterSecretStore target: name: db-credentials data: - secretKey: password remoteRef: key: production/db property: passwordContrôle 5 : Audit Logging et Détection
Sans logs d’audit, vous volez à l’aveugle. Activez l’audit au niveau API Server et cherchez ces patterns :
apiVersion: audit.k8s.io/v1kind: Policyrules:- level: RequestResponse resources: - group: "" resources: ["secrets", "configmaps"]- level: Metadata resources: - group: "" resources: ["pods", "services"]Signaux d’alerte à surveiller :
execdans des pods en production hors heures de bureau- Création de nouveaux ClusterRoleBindings
- Accès aux secrets depuis des IPs inhabituelles
- Téléchargements d’images depuis des registries non approuvés
Bilan
Implémenter ces cinq contrôles réduit drastiquement votre surface d’attaque. La priorité recommandée :
- RBAC audit et nettoyage (impact immédiat, effort faible)
- Network Policies sur les namespaces critiques (impact élevé, effort moyen)
- Pod Security Standards en mode
warnd’abord (transition douce) - Audit logging (visibilité immédiate)
- External Secrets (effort plus élevé, valeur à long terme)
La sécurité Kubernetes n’est pas un projet ponctuel. C’est un processus continu d’audit, de remédiation et d’amélioration. Commencez par ce qui fait le plus mal, mesurez, itérez.