Mettre à niveau un cluster Kubernetes sans temps d'arrêt

Mettre à niveau un cluster Kubernetes sans temps d'arrêt

Processus de mise à niveau pour votre cluster Kubernetes

À un moment donné, lors de l'utilisation d'un cluster Kubernetes, il devient nécessaire de mettre à jour les nœuds en cours d'exécution. Cela peut inclure des mises à jour de packages, des mises à jour du noyau ou le déploiement de nouvelles images de machine virtuelle. Dans la terminologie Kubernetes, cela s'appelle « Perturbation volontaire ».

Cet article fait partie d'une série de 4 articles :

  1. Ce post.
  2. Arrêt correct des pods dans un cluster Kubernetes
  3. Arrêt retardé d'un pod lors de sa suppression
  4. Comment éviter les temps d'arrêt du cluster Kubernetes à l'aide de PodDisruptionBudgets

(environ. Attendez-vous à des traductions des articles restants de la série dans un avenir proche)

Dans cet article, nous décrirons tous les outils fournis par Kubernetes pour atteindre zéro temps d'arrêt pour les nœuds exécutés dans votre cluster.

Définition du problème

Nous adopterons d'abord une approche naïve, identifierons les problèmes et évaluerons les risques potentiels de cette approche, et développerons des connaissances pour résoudre chacun des problèmes que nous rencontrons tout au long du cycle. Le résultat est une configuration qui utilise des hooks de cycle de vie, des sondes de préparation et des budgets de perturbation des pods pour atteindre notre objectif de zéro temps d'arrêt.

Pour commencer notre voyage, prenons un exemple concret. Disons que nous avons un cluster Kubernetes de deux nœuds, dans lequel une application s'exécute avec deux pods situés derrière Service:

Mettre à niveau un cluster Kubernetes sans temps d'arrêt

Commençons par deux pods avec Nginx et Service exécutés sur nos deux nœuds de cluster Kubernetes.

Nous souhaitons mettre à jour la version du noyau de deux nœuds de travail de notre cluster. Comment faisons-nous cela? Une solution simple consisterait à démarrer de nouveaux nœuds avec la configuration mise à jour, puis à arrêter les anciens nœuds tout en démarrant les nouveaux. Même si cela fonctionnera, cette approche posera quelques problèmes :

  • Lorsque vous désactivez les anciens nœuds, les pods qui s'y exécutent seront également désactivés. Que se passe-t-il si les pods doivent être effacés pour un arrêt progressif ? Le système de virtualisation que vous utilisez peut ne pas attendre la fin du processus de nettoyage.
  • Et si vous désactiviez tous les nœuds en même temps ? Vous bénéficierez d'un temps d'arrêt décent pendant que les pods se déplacent vers de nouveaux nœuds.

Nous avons besoin d'un moyen de migrer gracieusement les pods des anciens nœuds tout en garantissant qu'aucun de nos processus de travail n'est en cours d'exécution pendant que nous apportons des modifications au nœud. Ou lorsque nous effectuons un remplacement complet du cluster, comme dans l'exemple (c'est-à-dire que nous remplaçons les images de VM), nous souhaitons transférer les applications en cours d'exécution des anciens nœuds vers les nouveaux. Dans les deux cas, nous souhaitons empêcher les nouveaux pods de se planifier sur d'anciens nœuds, puis en expulser tous les pods en cours d'exécution. Pour atteindre ces objectifs, nous pouvons utiliser la commande kubectl drain.

Redistribuer tous les pods d'un nœud

L'opération de drainage vous permet de redistribuer tous les pods d'un nœud. Lors de l'exécution du drain, le nœud est marqué comme non planifiable (drapeau NoSchedule). Cela empêche de nouveaux pods d’apparaître dessus. Ensuite, drain commence à expulser les pods du nœud, arrête les conteneurs qui s'exécutent actuellement sur le nœud, envoyant un signal TERM conteneurs dans une nacelle.

Bien que kubectl drain fera un excellent travail pour expulser les pods, il existe deux autres facteurs qui peuvent provoquer l'échec de l'opération de drainage :

  • Votre candidature doit pouvoir se terminer gracieusement lors de la soumission TERM signal. Lorsque les pods sont expulsés, Kubernetes envoie un signal TERM conteneurs et attend qu'ils s'arrêtent pendant un laps de temps spécifié, après quoi, s'ils ne se sont pas arrêtés, il les termine de force. Dans tous les cas, si votre conteneur ne perçoit pas correctement le signal, vous pouvez toujours éteindre incorrectement les pods s'ils sont en cours d'exécution (par exemple, une transaction de base de données est en cours).
  • Vous perdez tous les pods qui contiennent votre application. Il peut ne pas être disponible lorsque de nouveaux conteneurs sont lancés sur de nouveaux nœuds, ou si vos pods sont déployés sans contrôleurs, ils peuvent ne pas redémarrer du tout.

Éviter les temps d'arrêt

Pour minimiser les temps d'arrêt dus à une interruption volontaire, telle qu'une opération de drainage sur un nœud, Kubernetes propose les options de gestion des pannes suivantes :

Dans le reste de la série, nous utiliserons ces fonctionnalités de Kubernetes pour atténuer l'impact de la migration des pods. Pour faciliter la compréhension de l'idée principale, nous utiliserons notre exemple ci-dessus avec la configuration de ressources suivante :

---
apiVersion: apps/v1
kind: Deployment
metadata:
 name: nginx-deployment
 labels:
   app: nginx
spec:
 replicas: 2
 selector:
   matchLabels:
     app: nginx
 template:
   metadata:
     labels:
       app: nginx
   spec:
     containers:
     - name: nginx
       image: nginx:1.15
       ports:
       - containerPort: 80
---
kind: Service
apiVersion: v1
metadata:
 name: nginx-service
spec:
 selector:
   app: nginx
 ports:
 - protocol: TCP
   targetPort: 80
   port: 80

Cette configuration est un exemple minimal Deployment, qui gère les pods nginx dans le cluster. De plus, la configuration décrit la ressource Service, qui peut être utilisé pour accéder aux pods nginx dans un cluster.

Tout au long du cycle, nous étendrons cette configuration de manière itérative afin qu'elle inclue à terme toutes les fonctionnalités fournies par Kubernetes pour réduire les temps d'arrêt.

Pour une version entièrement implémentée et testée des mises à jour du cluster Kubernetes pour un temps d'arrêt nul sur AWS et au-delà, visitez Gruntwork.io.

Lisez également d'autres articles sur notre blog:

Source: habr.com

Ajouter un commentaire