E-NO
Kubernetes 11 min de lecture

Dépannage réseau des CronJobs Kubernetes : guide pratique

calendar_today Publié : 2026-08-02
update Dernière mise à jour : 2026-08-02
analytics Efficacité SEO : 100%
Illustration du guide technique pour « Dépannage réseau des CronJobs Kubernetes : guide pratique ».

Introduction

Les CronJobs Kubernetes exécutent des Pods de courte durée pour effectuer des travaux planifiés. Contrairement aux Deployments de longue durée, ces Pods échouent souvent silencieusement entre deux exécutions. Les erreurs de configuration réseau sont une cause principale : résolution DNS, Services et ports du cluster, NetworkPolicies, ou contrôles de sortie (egress) au niveau des nœuds ou du cloud. Comme les CronJobs sont éphémères, il est plus difficile de les surprendre en flagrant délit.

Ce guide montre aux praticiens comment dépanner le réseau des CronJobs avec un rayon d'impact minimal. Vous allez inventorier l'environnement, créer un parcours diagnostique sûr, exécuter des tests ciblés pour le DNS et les ports, vérifier les résultats et récupérer proprement si un changement tourne mal. Tout est conçu pour être pratique et reproductible.

Inventaire des versions et de l'environnement

Avant de modifier quoi que ce soit, collectez les faits. Cela évite les suppositions et aide à trier au bon niveau.

Prérequis :

  • Accès kubectl au cluster et aux espaces de noms concernés
  • Capacité de créer un espace de noms temporaire et d'appliquer des manifestes
  • Familiarité de base avec les concepts CronJob, Job, Pod

Commandes d'inventaire :

  • Identifier les versions de Kubernetes et kubectl :
kubectl version --short
  • Lister les nœuds et indices CNI (les étiquettes du fournisseur peuvent indiquer le CNI et le mode réseau) :
kubectl get nodes -o wide
  • Confirmer la présence de CoreDNS et noter sa version d'image :
kubectl -n kube-system get deploy coredns -o yaml | grep -i image
  • Vérifier si NetworkPolicy est appliqué (Calico, Cilium, etc. étiquettent généralement leurs composants) :
kubectl get pods -A | grep -Ei "calico|cilium|weave|ovn|antrea"
  • Noter les espaces de noms et les CronJobs existants :
kubectl get ns
kubectl get cronjobs -A

Pour chaque CronJob cible, capturez sa spécification comme sauvegarde avant toute modification :

kubectl -n VOTRE_NS get cronjob VOTRE_CRON -o yaml > VOTRE_CRON.backup.yaml

Enregistrez les éléments suivants :

  • Version de Kubernetes et localisation cloud/on-prem
  • Version de CoreDNS
  • Présence de contrôleurs NetworkPolicy
  • Contrôle de la sortie sortante : NetworkPolicy, pare-feu nœud, ou groupes de sécurité cloud

Question rapide 1 sur 2

Que fait le contrôleur CronJob lorsqu'il y a plus de 100 planifications manquées depuis la dernière planification ?

La référence indique : « S'il y a plus de 100 planifications manquées, alors il ne démarre pas le Job et enregistre l'erreur. »

Parcours de configuration sûr

Utilisez un pilote étroit et mesurable pour observer les résultats sans impacter les charges de production. Les étapes ci-dessous créent un parcours diagnostique à faible risque.

  1. Créez un espace de noms de test isolé :
kubectl create ns jobs-test
  1. Créez un CronJob de sondage minimal avec des étiquettes explicites et des politiques conservatrices. Cet exemple construit effectue des recherches DNS, une requête HTTPS externe, et une sonde de port vers un nom de Service. Ajustez les cibles selon votre environnement.

Manifeste d'exemple :

apiVersion: batch/v1
kind: CronJob
metadata:
  name: net-check
  namespace: jobs-test
spec:
  schedule: "*/10 * * * *"
  concurrencyPolicy: Forbid
  startingDeadlineSeconds: 60
  successfulJobsHistoryLimit: 1
  failedJobsHistoryLimit: 1
  jobTemplate:
    spec:
      backoffLimit: 0
      template:
        metadata:
          labels:
            app: net-check
        spec:
          restartPolicy: Never
          containers:
          - name: busybox
            image: busybox:1.36
            command: ["sh","-lc
t            args:
            - |
              set -eu
              echo "Test DNS..."
              nslookup kubernetes.default.svc.cluster.local || exit 12
              nslookup example.com || exit 13
              echo "Test HTTP..."
              wget -q --spider --timeout=5 https://example.com || exit 14
              echo "Test de port vers un Service..."
              nc -vz -w5 my-service.my-namespace.svc.cluster.local 5432 || true
              echo "Tous les tests tentés"

Notes :

  • L'image est choisie pour sa simplicité. Si une commande manque dans votre image de base, changez d'outils ou lancez des diagnostics ad-hoc (voir ci-dessous).
  • Le test de port utilise un nom de Service et un port hypothétiques. Remplacez par une cible réelle dans le cluster (par exemple postgres.database.svc.cluster.local 5432).
  • backoffLimit: 0 empêche les relances automatiques qui pollueraient les logs.
  • concurrencyPolicy: Forbid évite les exécutions chevauchantes lors de tests répétés.
  1. Ajoutez optionnellement une NetworkPolicy ciblée pour prouver ou infirmer les hypothèses DNS/sortie. Commencez étroit, puis élargissez. Cet exemple autorise le DNS vers CoreDNS (par espace de noms) et le TCP/443 sortant vers Internet. Restreignez ipBlock à vos vrais CIDR de sortie quand possible.
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-dns-and-https
  namespace: jobs-test
spec:
  podSelector:
    matchLabels:
      app: net-check
  policyTypes:
  - Egress
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: kube-system
    ports:
    - protocol: UDP
      port: 53
    - protocol: TCP
      port: 53
  - to:
    - ipBlock:
        cidr: 0.0.0.0/0
      ports:
      - protocol: TCP
        port: 443
  1. Appliquez et lancez un Job unique basé sur le modèle du CronJob pour ne pas attendre la planification :
kubectl -n jobs-test apply -f net-check.yaml
kubectl -n jobs-test create job --from=cronjob/net-check net-check-now
  1. Observez la sortie et le code de sortie :
kubectl -n jobs-test logs job/net-check-now
kubectl -n jobs-test get job net-check-now -o jsonpath='{.status.succeeded}{"\n"}'
  1. Pour une sonde interactive, lancez un Pod diagnostique ad-hoc et testez la résolution de noms et la connectivité dans le cluster :
kubectl -n jobs-test run diag --rm -it --image=busybox:1.36 --restart=Never -- sh

À l'intérieur du shell :

cat /etc/resolv.conf
nslookup kubernetes.default.svc.cluster.local
nslookup example.com
wget -q --spider --timeout=5 https://example.com
nc -vz -w5 my-service.my-namespace.svc.cluster.local 5432

Vérification et diagnostics

Interprétez ce que vous voyez avec une séquence de vérifications ciblées. Ne changez qu'une variable à la fois.

1. Confirmer que le Job a réellement démarré

Attendu en cas de succès : status.succeeded=1, pas de dépassement de backoff, phase du Pod à Succeeded.

kubectl -n jobs-test get jobs
kubectl -n jobs-test describe job net-check-now

2. Vérifier les événements et logs du Pod

Cherchez les timeouts, connexions refusées, ou erreurs de résolution de nom.

kubectl -n jobs-test get pods -l job-name=net-check-now
kubectl -n jobs-test describe pod NOM_DU_POD
kubectl -n jobs-test logs NOM_DU_POD

3. Vérifications DNS

Attendu : peu ou pas de lignes SERVFAIL ou timeout corrélées à l'heure de démarrage de votre Job.

  • Inspecter la configuration du résolveur depuis un Pod similaire :
kubectl -n jobs-test exec -it DEPLOYMENT_OU_POD -- cat /etc/resolv.conf
  • Le ndots=5 typique signifie qu'un nom court comme example.com déclenche plusieurs recherches dans le chemin de recherche d'abord. Utilisez un point final pour les noms absolus (example.com.) ou des FQDN complets pour éviter les délais du chemin de recherche dans les Pods de courte durée.
  • Vérifier la santé de CoreDNS et les erreurs de requête :
kubectl -n kube-system logs deploy/coredns --tail=200 | grep -Ei "timeout|servfail|refused|dns" || true

4. Vérifications Service et Endpoints (cibles dans le cluster)

Attendu : le Service a au moins un endpoint. Si les endpoints sont vides, les Pods de support ne sont pas prêts ou les sélecteurs sont incorrects.

kubectl -n mon-namespace get svc mon-service -o wide
kubectl -n mon-namespace get endpoints mon-service -o wide

5. Vérifications NetworkPolicy

Attendu : s'il y a une politique de refus par défaut en sortie, vous devez autoriser explicitement le DNS et les destinations requises.

  • Lister les politiques dans l'espace de noms du CronJob et l'espace de noms cible :
kubectl -n jobs-test get networkpolicy
kubectl -n mon-namespace get networkpolicy
  • Examiner les règles qui pourraient sélectionner les Pods du CronJob par étiquette ou espace de noms :
kubectl -n jobs-test describe networkpolicy NOM

6. Sortie sortante et pare-feux nœud ou cloud

Attendu : les nœuds peuvent atteindre les adresses externes requises sur les ports nécessaires.

  • Si le DNS fonctionne mais que HTTPS vers Internet échoue, vérifiez si votre environnement restreint la sortie :
  • Cloud : vérifiez que le groupe de sécurité du nœud ou les règles de pare-feu autorisent le TCP/443 et UDP/TCP/53 sortants.
  • On-prem : confirmez que les pare-feux nœuds autorisent UDP/TCP/53 vers CoreDNS et les ports externes requis, et que le NAT est disponible.

7. Santé de kube-proxy et routage

Attendu : pas d'erreurs répétées de synchronisation ou iptables/ipvs au moment de l'exécution du Job.

  • Si un Service ClusterIP est inaccessible mais que les endpoints existent, le problème peut venir de kube-proxy ou du routage nœud. Vérifiez les logs kube-proxy pour erreurs (espace de noms généralement kube-system) :
kubectl -n kube-system logs -l k8s-app=kube-proxy --tail=200

Symptômes courants, causes probables, et quoi vérifier

Symptôme ou chaîne de logCause probableQuoi vérifier
no such hostÉchec DNS ou sortie DNS bloquéenslookup dans le Pod ; logs CoreDNS ; NetworkPolicy pour UDP/TCP 53
i/o timeoutSortie bloquée ou endpoint distant inaccessiblePare-feu cloud/nœud ; règles ipBlock ; alternative traceroute (curl/wget -m)
connection refusedPort cible fermé ou mauvais Service/portService .spec.ports, Endpoints, listener de l'application cible
Endpoints videsSélecteurs incompatibles ou Pods pas ReadySélecteur Service ; étiquettes Pod ; readiness gates
BackoffLimitExceededJob n'a pas réussi dans les relancesDéfaillance réseau sous-jacente ; timeout trop court dans le script

Sorties attendues (exemples construits)

  • Succès DNS :
nslookup example.com
Server: 10.96.0.10
Address: 10.96.0.10:53
Name: example.com
Address: 93.184.216.34
  • Succès HTTPS :
wget -q --spider --timeout=5 https://example.com retourne le code de sortie 0
  • Sonde de port Service (hypothétique) :
nc -vz -w5 postgres.database.svc.cluster.local 5432 affiche succeeded ou timeout si bloqué

Resserrer ou élargir la portée en toute sécurité

  • Si le DNS échoue, autorisez d'abord seulement UDP/TCP 53 vers kube-system (CoreDNS). N'ouvrez pas 0.0.0.0/0 tant que vous n'avez pas prouvé que c'est nécessaire.
  • Si le HTTPS externe est requis, autorisez seulement les CIDR ou noms d'hôtes connus via un proxy si disponible.
  • Étiquetez toujours le template de Pod de votre CronJob (par exemple app: net-check) pour que les NetworkPolicies puissent cibler précisément.

Question rapide 2 sur 2

Quelle annotation Kubernetes ajoute aux Jobs créés par un CronJob à partir de la version 1.32 ?

La référence indique : « À partir de Kubernetes v1.32, les CronJobs appliquent une annotation `batch.kubernetes.io/cronjob-scheduled-timestamp` à leurs Jobs créés. »

Modes de défaillance et récupération

Préparez des sorties sûres pendant les tests et le déploiement.

1. Mettre en pause ou arrêter les exécutions rapidement

  • Suspendre un CronJob pour empêcher de nouveaux Jobs pendant l'investigation :
kubectl -n jobs-test patch cronjob net-check -p '{"spec": {"suspend": true}}'
  • Supprimer les Jobs en attente créés par la planification :
kubectl -n jobs-test delete job -l job-name=net-check

2. Restaurer les manifestes

  • Restaurer un CronJob depuis la sauvegarde créée plus tôt :
kubectl -n VOTRE_NS apply -f VOTRE_CRON.backup.yaml
  • Revenir sur la NetworkPolicy en supprimant la politique de test ou en réappliquant la version antérieure :
kubectl -n jobs-test delete networkpolicy allow-dns-and-https

3. Contenir le rayon d'impact

  • Utilisez backoffLimit: 0 et des timeouts courts (par exemple wget --timeout=5) dans les Jobs de test pour éviter les attentes longues.
  • Préférez concurrencyPolicy: Forbid pour bloquer les chevauchements qui pourraient stresser les services en aval.

4. Vérifier la récupération

  • Après un rollback, relancez un Job unique pour confirmer que le système se comporte comme avant :
kubectl -n jobs-test create job --from=cronjob/net-check net-check-verify
kubectl -n jobs-test logs job/net-check-verify
  • Assurez-vous que vos CronJobs de production critiques ne sont pas affectés :
kubectl -n NS_PROD get jobs --sort-by=.metadata.creationTimestamp | tail -n 5

Causes racines typiques et remèdes

Cause racineRemède minimalÉtape de vérification
Politique de refus par défaut en sortie bloque le DNSAutoriser sortie UDP/TCP 53 vers kube-systemnslookup kubernetes.default.svc.cluster.local réussit
Mauvais nom de Service ou portCorriger le DNS ou le port du Service et redéployernc -vz vers le nom:port corrigé réussit
Sortie externe bloquéeOuvrir TCP/443 (ou port requis) vers CIDR autoriséswget --spider https://cible.exemple retourne code 0
Délais du chemin de recherche du résolveurUtiliser FQDN ou point final ; réduire les recherchesLatence requête DNS chute ; Job sort plus tôt
Endpoints manquants à cause des étiquettesCorriger le sélecteur Service pour matcher les Podskubectl get endpoints montre des adresses prêtes

Liste de contrôle opérationnelle

Utilisez ceci comme runbook reproductible. Remplacez les placeholders par vos valeurs.

ÉtapeCommande ou actionRésultat attendu
Sauvegarder CronJobkubectl -n NS get cronjob NAME -o yaml > NAME.bak.yamlFichier de sauvegarde créé
Créer ns testkubectl create ns jobs-testEspace de noms existe
Appliquer CronJob testkubectl -n jobs-test apply -f net-check.yamlCronJob créé
Exécution uniquekubectl -n jobs-test create job --from=cronjob/net-check net-check-nowJob créé
Obtenir logskubectl -n jobs-test logs job/net-check-nowVérifications DNS/HTTP visibles
Inspecter événements Podkubectl -n jobs-test describe pod PODErreurs ou succès clairs
Vérifier logs CoreDNSkubectl -n kube-system logs deploy/coredns --tail=200Pas de timeouts DNS ou SERVFAIL à l'exécution
Vérifier endpoints Servicekubectl -n NS_APP get endpoints SVCEndpoints non vides
Appliquer politique sortiekubectl -n jobs-test apply -f allow-dns-and-https.yamlPolitique en place
Relancer et vérifierkubectl -n jobs-test create job --from=cronjob/net-check net-check-againSuccède ou échec plus clair
Suspendre si besoinkubectl -n jobs-test patch cronjob net-check -p '{"spec":{"suspend":true}}'Nouveaux Jobs arrêtés
Annuler politiquekubectl -n jobs-test delete networkpolicy allow-dns-and-httpsPolitique supprimée

Conclusion

Les CronJobs sont particulièrement sensibles aux frictions réseau car ils sont de courte durée et planifiés. Le chemin le plus rapide vers la cause racine est de commencer par un pilote étroit et observable : inventoriez votre environnement, lancez un CronJob diagnostique sûr, et testez le DNS, les endpoints de Service, et la sortie dans cet ordre. Ajoutez ou ajustez les NetworkPolicies avec précision, préférez les noms de domaine absolus pour éviter les pièges du résolveur, et gardez le backoff et les timeouts conservateurs pendant les tests. Si un changement se retourne contre vous, suspendez le CronJob, restaurez la politique ou la spec depuis la sauvegarde, et vérifiez avec une exécution unique.

Adoptez la liste de contrôle de ce guide comme votre runbook. Chaque fois que vous ajoutez un nouveau CronJob avec des dépendances réseau, créez une variante diagnostique courte, prouvez la connectivité en isolation, et seulement alors planifiez-le. Cela maintient les incidents petits, les correctifs rapides, et les résultats prévisibles.

Recherches connexes

Score de qualité de l’article

Utilité pour le lecteur 100%
  • check_circle Guide prêt à lire
  • check_circle Exemples pratiques inclus
  • check_circle URL d’article optimisée pour le SEO