Introduction
Les Secrets Kubernetes sont un composant essentiel pour gérer les données sensibles comme les mots de passe, les jetons et les clés SSH. Cependant, à mesure que les clusters évoluent, la façon dont les Secrets sont stockés, montés et consommés peut introduire des goulots d'étranglement de performance qui affectent le temps de démarrage des applications, la charge sur le serveur d'API et l'utilisation des ressources des nœuds. Cet article fournit des conseils pratiques pour régler les performances des Secrets Kubernetes, avec des exemples concrets et des commandes pour vous aider à observer, diagnostiquer et optimiser votre configuration en toute sécurité.
Nous nous concentrons sur les besoins des développeurs, des consultants DevOps et des équipes techniques de startups qui doivent passer d'un problème observé à un résultat vérifié. Nous couvrons les domaines clés : l'inventaire des versions et de l'environnement, les chemins de configuration sûrs, la vérification et le diagnostic, les modes de défaillance et la récupération, et une liste de contrôle opérationnelle. Chaque section comprend des commandes, des sorties attendues et des points de décision pour assurer la sécurité opérationnelle.
L'objectif est la sécurité opérationnelle : observer avant de modifier, limiter le rayon d'impact, utiliser des espaces réservés au lieu de secrets dans les commandes, vérifier le résultat et documenter comment récupérer si l'état attendu n'est pas atteint.
Inventaire des versions et de l'environnement
Avant de régler les performances des Secrets, vous devez savoir exactement avec quoi vous travaillez. Cette section vous aide à inventorier votre version de Kubernetes, les composants pertinents, les prérequis et l'état actuel de l'utilisation des Secrets. Séparez l'observation de l'intervention : capturez d'abord l'état actuel et les horodatages, protégez les informations d'identification et le matériel privé, puis modifiez un seul élément délimité uniquement lorsque son rayon d'impact et son chemin de récupération sont compris.
Vérifier la version de Kubernetes et les composants
Commencez par vérifier la version de votre cluster et les composants impliqués dans la gestion des Secrets.
kubectl version --short
Sortie attendue (exemple) :
Client Version: v1.27.3
Kustomize Version: v5.0.1
Server Version: v1.27.3
Les versions du serveur d'API et du kubelet sont importantes car la gestion des Secrets a évolué. Par exemple, le champ Immutable pour les Secrets a été introduit en v1.21, et son utilisation peut réduire la charge sur le serveur d'API.
Vérifiez la version du kubelet sur un nœud :
kubectl get nodes -o wide
Notez la colonne VERSION. Si vous avez des versions mixtes, standardisez avant de procéder au réglage.
Inventorier les Secrets existants et leur utilisation
Listez tous les Secrets dans un espace de noms :
kubectl get secrets -n my-app
Exemple de sortie :
NAME TYPE DATA AGE
db-credentials Opaque 2 30d
api-token kubernetes.io/service-account-token 3 30d
tls-cert kubernetes.io/tls 2 30d
Comptez le nombre total de Secrets dans le cluster :
kubectl get secrets --all-namespaces | wc -l
Un grand nombre de Secrets peut augmenter l'utilisation de la mémoire du serveur d'API et le trafic des événements de surveillance. Si vous avez des milliers de Secrets, envisagez la consolidation ou l'utilisation de systèmes de gestion de secrets externes.
Identifier les pods qui montent des Secrets
Trouvez quels pods utilisent des Secrets :
kubectl get pods --all-namespaces -o json | jq -r '.items[] | select(.spec.volumes[]?.secret != null) | .metadata.namespace + "/" + .metadata.name'
Cette commande utilise jq pour filtrer les pods avec des volumes de secrets. Si vous n'avez pas jq, installez-le ou utilisez kubectl get pods -o yaml et inspectez manuellement.
Évaluer la taille et le contenu des Secrets
La taille d'un Secret est limitée à 1 Mio par Secret (en réalité 1 Mio pour l'objet entier y compris les métadonnées, mais les valeurs individuelles sont également limitées à 1 Mio). Les Secrets volumineux peuvent causer des problèmes de performance lorsqu'ils sont montés, car le kubelet les écrit dans tmpfs. Vérifiez la taille d'un Secret :
kubectl get secret db-credentials -n my-app -o jsonpath='{.data}' | wc -c
Cela donne la taille des données encodées. Décodez pour obtenir la taille réelle :
kubectl get secret db-credentials -n my-app -o go-template='{{range $k,$v := .data}}{{$k}}: {{$v | base64decode | len}}{{"\n"}}{{end}}'
Sortie attendue :
password: 12
username: 8
Si une clé individuelle est volumineuse (par exemple, un paquet de certificats), envisagez de la diviser ou d'utiliser un mécanisme différent comme une ConfigMap (pour les données non sensibles volumineuses) ou un pilote CSI.
Vérification pratique : observation en lecture seule
Avant d'apporter des modifications, exécutez ces commandes en lecture seule pour établir une base de référence :
kubectl get pods -o wide
kubectl describe pod <pod-name>
kubectl logs <pod-name> --previous
kubectl rollout status deployment/<deployment-name>
Par exemple, pour décrire un pod utilisant un Secret :
kubectl describe pod web-7d8f9b6c4-abcde -n my-app
Recherchez les événements liés au montage de volume ou à la récupération du Secret. Si vous voyez des erreurs FailedMount, cela indique un problème.
Gardez le test local petit : appliquez un manifeste, inspectez les ressources générées et vérifiez le trafic avec kubectl port-forward ou un type de service local avant de passer à un équilibreur de charge cloud ou à un contrôleur d'entrée.
Chemin de configuration sûr
Cette section décrit les modifications de configuration sûres pour améliorer les performances des Secrets. Chaque modification doit être appliquée progressivement et vérifiée.
Utiliser des Secrets immuables
Si vos Secrets ne changent pas fréquemment, marquez-les comme immuables. Les Secrets immuables réduisent la charge sur le serveur d'API car le kubelet n'a pas besoin de surveiller les changements, et le serveur d'API peut les servir plus efficacement.
Exemple de manifeste de Secret avec immutable: true :
apiVersion: v1
kind: Secret
metadata:
name: db-credentials
namespace: my-app
immutable: true
type: Opaque
data:
username: dXNlcg== # base64 "user"
password: cGFzcw== # base64 "pass"
Ne définissez un Secret comme immuable que si vous êtes sûr qu'il n'aura pas besoin d'être mis à jour. Si vous devez le modifier plus tard, vous devrez le supprimer et le recréer, ce qui peut entraîner une indisponibilité pour les pods qui l'utilisent. Pour vérifier si un Secret est immuable :
kubectl get secret db-credentials -n my-app -o jsonpath='{.immutable}'
Sortie attendue : true ou vide (si non défini).
Optimiser les montages de Secrets
Lorsque vous montez des Secrets en tant que volumes, considérez ce qui suit :
- Monter uniquement les clés nécessaires : Au lieu de monter tout le Secret, spécifiez uniquement les clés dont votre application a besoin. Cela réduit la quantité de données écrites dans le système de fichiers du pod et peut améliorer le temps de démarrage.
Exemple de spécification de pod :
spec:
containers:
- name: app
image: myapp:1.0
volumeMounts:
- name: secret-volume
mountPath: /etc/secrets
readOnly: true
volumes:
- name: secret-volume
secret:
secretName: db-credentials
items:
- key: username
path: db-username
- Utiliser
defaultModepour contrôler les permissions des fichiers : Le mode par défaut est 0644 ; définissez-le à une valeur plus restrictive si nécessaire (par exemple, 0400) pour réduire l'exposition. Cela a un impact négligeable sur les performances mais c'est une bonne pratique de sécurité.
- Éviter de monter les Secrets comme variables d'environnement pour les Secrets volumineux : Les variables d'environnement sont stockées dans la mémoire du pod, et les valeurs volumineuses peuvent augmenter l'utilisation de la mémoire. Les montages de volume sont généralement plus efficaces pour les données volumineuses car ils sont soutenus par tmpfs et peuvent être lus à la demande.
Réduire les surveillances de Secrets
Chaque pod qui monte un Secret amène le kubelet à surveiller ce Secret sur le serveur d'API. Si vous avez de nombreux pods montant le même Secret, envisagez d'utiliser un volume projeté pour combiner plusieurs Secrets en un seul, réduisant le nombre de surveillances.
Exemple d'utilisation d'un volume projeté :
volumes:
- name: all-secrets
projected:
sources:
- secret:
name: db-credentials
- secret:
name: api-token
Cela monte les deux Secrets dans un seul volume, et le kubelet maintient une seule surveillance pour le volume projeté au lieu de surveillances séparées.
Utiliser la gestion de secrets externe
Pour les secrets très volumineux ou changeant fréquemment, envisagez d'utiliser un système de gestion de secrets externe comme HashiCorp Vault, AWS Secrets Manager ou Azure Key Vault avec un pilote CSI (par exemple, Secrets Store CSI Driver). Cela décharge le stockage et la gestion des Secrets de Kubernetes et peut améliorer les performances en réduisant la charge sur le serveur d'API.
Exemple d'installation du Secrets Store CSI Driver (helm) :
helm repo add secrets-store-csi-driver https://kubernetes-sigs.github.io/secrets-store-csi-driver/charts
helm install csi-secrets-store secrets-store-csi-driver/secrets-store-csi-driver --namespace kube-system
Après l'installation, vous pouvez créer une SecretProviderClass pour synchroniser les secrets externes dans un Secret Kubernetes ou les monter directement.
Vérifier les modifications de configuration
Après avoir appliqué une modification de configuration, vérifiez que les pods démarrent correctement et que les Secrets sont montés comme prévu.
kubectl apply -f updated-pod.yaml
kubectl rollout status deployment/my-app
kubectl exec -it <pod-name> -- ls -l /etc/secrets
Sortie attendue (exemple) :
total 0
-r--r--r-- 1 root root 12 Mar 10 12:00 db-username
Vérifiez que le contenu du fichier correspond à la valeur du Secret (sans exposer de vrais secrets dans les journaux) :
kubectl exec -it <pod-name> -- cat /etc/secrets/db-username
Si le pod ne démarre pas, utilisez kubectl describe pod et kubectl logs pour diagnostiquer.
Vérification et diagnostics
La vérification et les diagnostics sont essentiels pour s'assurer que vos efforts de réglage améliorent réellement les performances. Cette section fournit des méthodes concrètes pour mesurer et diagnostiquer les performances liées aux Secrets.
Mesurer la latence de récupération des Secrets
Une préoccupation courante en matière de performance est le temps nécessaire pour qu'un pod démarre et que les Secrets soient disponibles. Vous pouvez mesurer cela en chronométrant le démarrage du pod.
Créez un pod de test qui monte un Secret et mesurez le temps jusqu'à ce qu'il devienne Ready :
time kubectl run secret-test --image=busybox --restart=Never -- sleep 3600
Mais cela ne monte pas de Secret. Pour tester avec un Secret, utilisez un manifeste :
apiVersion: v1
kind: Pod
metadata:
name: secret-test
namespace: my-app
spec:
containers:
- name: test
image: busybox
command: ['sh', '-c', 'echo Secret mounted; sleep 3600']
volumeMounts:
- name: secret-volume
mountPath: /etc/secret
readOnly: true
volumes:
- name: secret-volume
secret:
secretName: db-credentials
Appliquez et chronométrez :
kubectl delete pod secret-test -n my-app --ignore-not-found
start=$(date +%s)
kubectl apply -f secret-test.yaml
kubectl wait --for=condition=Ready pod/secret-test -n my-app --timeout=60s
end=$(date +%s)
echo "Pod ready in $((end-start)) seconds"
Un temps typique est de 2 à 5 secondes, selon la taille du cluster et du Secret. Si cela prend plus de temps, enquêtez.
Vérifiez si le Secret est monté correctement :
kubectl exec secret-test -n my-app -- ls /etc/secret
Diagnostiquer la charge du serveur d'API
Si de nombreux pods montent le même Secret, le serveur d'API peut recevoir un nombre élevé de requêtes de surveillance. Vérifiez les métriques du serveur d'API si vous avez metrics-server ou Prometheus.
Pour une vérification rapide, regardez les journaux du serveur d'API pour les requêtes liées aux Secrets :
kubectl logs -n kube-system kube-apiserver-<node-name> | grep 'secrets'
Remarque : L'accès aux journaux du serveur d'API peut nécessiter des autorisations spéciales.
Alternativement, utilisez kubectl get --raw /metrics pour obtenir des métriques (si activé) et cherchez apiserver_request_total avec resource=secrets.
Utiliser kubectl describe pour trouver des événements
Pour un pod lent à démarrer ou en échec, vérifiez les événements :
kubectl describe pod <pod-name> -n my-app
Recherchez des événements comme :
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal Scheduled 10m default-scheduler Successfully assigned my-app/web-... to node-1
Warning FailedMount 9m kubelet Unable to mount volumes for pod "web-...": timeout expired waiting for volumes to attach or mount for pod
Warning FailedMount 8m kubelet MountVolume.SetUp failed for volume "secret-volume" : secret "db-credentials" not found
Cela indique que le Secret n'existe pas ou n'est pas accessible.
Surveiller l'utilisation des ressources du nœud
Les volumes de Secrets sont montés en tmpfs, donc ils consomment de la mémoire sur le nœud. Les Secrets volumineux montés par de nombreux pods peuvent augmenter l'utilisation de la mémoire. Vérifiez la pression mémoire du nœud :
kubectl top nodes
Si l'utilisation de la mémoire est élevée, envisagez de réduire la taille du Secret ou d'utiliser un stockage externe.
Utiliser des outils de traçage et de profilage
Pour une analyse plus approfondie, vous pouvez utiliser des outils comme kubectl trace (du plugin kubectl-trace) ou strace à l'intérieur d'un pod pour tracer l'accès aux fichiers des volumes de Secrets. Cependant, ces outils sont avancés et souvent pas nécessaires pour le réglage de performance typique.
Vérification pratique pour les mises à jour de Secrets
Si vous mettez à jour un Secret, combien de temps faut-il pour que les pods voient la nouvelle valeur ? Par défaut, le kubelet synchronise les Secrets périodiquement (environ 1 minute) ou lorsqu'un événement de surveillance se produit. Avec les Secrets immuables, aucune mise à jour n'est attendue, donc ce n'est pas une préoccupation. Pour les Secrets mutables, vous pouvez tester :
Mettez à jour le Secret :
kubectl create secret generic db-credentials --from-literal=password=newpass --dry-run=client -o yaml | kubectl apply -f -
Puis vérifiez à l'intérieur du pod après un certain temps :
kubectl exec <pod-name> -- cat /etc/secrets/password
Cela peut prendre jusqu'à une minute pour refléter le changement. Si les applications ont besoin de mises à jour immédiates, elles doivent surveiller le système de fichiers ou utiliser un autre mécanisme.
Modes de défaillance et récupération
Même avec un réglage soigneux, des défaillances peuvent survenir. Cette section couvre les modes de défaillance courants liés aux performances des Secrets et comment récupérer.
Secret introuvable
Si un pod échoue avec MountVolume.SetUp failed ... secret "<name>" not found, le Secret peut être absent de l'espace de noms ou mal orthographié.
Vérifiez :
kubectl get secrets -n my-app
S'il est manquant, créez-le ou corrigez la référence. Pour récupérer, modifiez le pod pour référencer le bon Secret ou créez le Secret.
Secret trop volumineux
Si vous dépassez la limite de 1 Mio, le serveur d'API rejettera la création du Secret avec une erreur comme :
The Secret "large-secret" is invalid: data: Too long: must have at most 1048576 bytes
Récupération : divisez le Secret en parties plus petites ou utilisez un mécanisme de stockage différent (par exemple, ConfigMap pour les données non sensibles, ou un magasin de secrets externe).
Permission refusée sur les fichiers montés
Si l'application ne peut pas lire les fichiers du Secret, vérifiez le defaultMode. Par exemple, s'il est défini à 0000, les fichiers sont illisibles. Changez defaultMode à une valeur raisonnable (par exemple, 0400 ou 0644) et réappliquez.
Latence élevée du serveur d'API due à de nombreuses surveillances
Symptômes : la latence du serveur d'API augmente, et de nombreuses requêtes watch pour les Secrets sont observées.
Récupération :
- Réduisez le nombre de pods montant le même Secret (par exemple, utilisez un volume projeté ou partagez via un compte de service si possible).
- Marquez les Secrets comme immuables pour réduire la charge de surveillance.
- Utilisez la gestion de secrets externe avec un pilote CSI pour contourner complètement les Secrets Kubernetes.
Pression mémoire du nœud due aux montages de Secrets volumineux
Si les nœuds subissent une pression mémoire, identifiez quels Secrets sont volumineux et combien de pods les montent.
Utilisez :
kubectl get secrets --all-namespaces -o json | jq -r '.items[] | [.metadata.namespace, .metadata.name, (.data | to_entries | map(.value | @base64d | length) | add // 0)] | @tsv' | sort -k3 -n -r | head
Cela affiche les principaux Secrets par taille totale de données. Ensuite, réduisez la taille ou limitez le montage.
Données de Secret corrompues
Si les données d'un Secret sont corrompues (par exemple, mauvais encodage base64), le pod peut le monter mais l'application échoue. Vérifiez en décodant :
kubectl get secret <name> -n <ns> -o jsonpath='{.data.key}' | base64 -d
Si corrompu, recréez le Secret avec des valeurs correctes.
Vérification de la récupération
Après toute action de récupération, vérifiez que les pods fonctionnent et que les Secrets sont accessibles :
kubectl rollout status deployment/<name>
kubectl exec <pod> -- ls /etc/secrets
kubectl exec <pod> -- cat /etc/secrets/<file>
Documentez toujours la modification et les étapes de vérification effectuées.
Liste de contrôle opérationnelle
Utilisez cette liste de contrôle pour évaluer et régler systématiquement les performances des Secrets Kubernetes.
- Vérification de la version
- Exécutez
kubectl version --short. - Assurez-vous que tous les nœuds et le plan de contrôle sont sur une version prise en charge (idéalement v1.21+ pour les Secrets immuables).
- Enregistrez la version pour référence.
- Métriques de base
- Comptez les Secrets :
kubectl get secrets --all-namespaces | wc -l. - Identifiez les plus grands Secrets en utilisant la commande de la section précédente.
- Mesurez le temps de démarrage du pod avec un montage de Secret (comme indiqué dans la vérification).
- Évaluer l'utilisation des Secrets
- Listez les pods montant des Secrets avec la commande
jq. - Déterminez si un Secret est monté par de nombreux pods (par exemple, >50 pods).
- Vérifiez si les Secrets sont fréquemment mis à jour (regardez les horodatages de création/mise à jour).
- Appliquer les optimisations (une à la fois)
- Marquez les Secrets immuables qui sont statiques.
- Utilisez
itemspour monter uniquement les clés requises. - Envisagez des volumes projetés pour plusieurs Secrets.
- Pour les secrets très volumineux ou dynamiques, planifiez la migration vers la gestion de secrets externe.
- Vérifier après chaque modification
- Appliquez la modification à un espace de noms de test ou à un déploiement canari.
- Surveillez le temps de démarrage du pod et les métriques du serveur d'API.
- Revenez en arrière si les performances se dégradent ou si des erreurs surviennent.
- Documenter et automatiser
- Mettez à jour les procédures opérationnelles avec les commandes et les sorties attendues.
- Ajoutez des contrôles à votre pipeline CI/CD (par exemple, valider la taille du Secret, l'immuabilité).
- Planifiez des audits réguliers de l'utilisation des Secrets.
Exemple de script de validation simple en CI (utilisant kubectl) :
#!/bin/bash
# Vérifier les Secrets trop volumineux
kubectl get secrets --all-namespaces -o json | jq -r '.items[] | select((.data | to_entries | map(.value | @base64d | length) | add) > 1000000) | .metadata.namespace + "/" + .metadata.name'
Si une sortie est produite, faites échouer le pipeline ou envoyez une notification.
Conclusion
Le réglage des performances des Secrets Kubernetes est essentiel pour maintenir un cluster réactif et fiable. En suivant les pratiques de cet article — en commençant par un inventaire complet, en apportant des modifications de configuration sûres, en vérifiant les résultats avec des métriques concrètes et en se préparant aux défaillances — vous pouvez éviter les goulots d'étranglement courants et garantir que vos applications ont un accès sécurisé et efficace aux secrets.
Chaque recommandation est limitée à une version, observable et réversible lorsque c'est possible. Copier une commande sans vérifier les prérequis et la sortie attendue n'est pas une procédure opérationnelle. Au lieu de cela, adoptez une approche systématique : observez, changez une chose, vérifiez et documentez.
Comme prochaine étape, choisissez une vérification à faible risque de la liste de contrôle opérationnelle, enregistrez l'état actuel, exécutez la vérification documentée, comparez le résultat avec le signal attendu et examinez les dépendances telles que ConfigMap, Service Account et Role. Un flux de travail technique fiable rend les défaillances visibles, protège les valeurs sensibles, limite les modifications à la ressource prévue et définit la vérification de récupération avant qu'un incident ne force la décision.
Avec ces outils et exemples, vous pouvez régler en toute confiance les performances des Secrets Kubernetes pour répondre aux demandes de votre cluster en croissance.