View a markdown version of this page

Exécution d'applications à haute disponibilité - Amazon EKS

Les traductions sont fournies par des outils de traduction automatique. En cas de conflit entre le contenu d'une traduction et celui de la version originale en anglais, la version anglaise prévaudra.

Exécution d'applications à haute disponibilité

Vos clients s'attendent à ce que votre application soit toujours disponible, y compris lorsque vous apportez des modifications et en particulier pendant les pics de trafic. Une architecture évolutive et résiliente permet à vos applications et services de fonctionner sans interruption, ce qui garantit la satisfaction de vos utilisateurs. Une infrastructure évolutive se développe et se réduit en fonction des besoins de l'entreprise. L'élimination des points de défaillance uniques est une étape cruciale pour améliorer la disponibilité d'une application et la rendre résiliente.

Avec Kubernetes, vous pouvez exploiter vos applications et les exécuter de manière hautement disponible et résiliente. Sa gestion déclarative garantit qu'une fois que vous avez configuré l'application, Kubernetes essaiera en permanence de faire correspondre l'état actuel à l'état souhaité.

Recommandations

Configurer les budgets relatifs à l'interruption des activités

https://kubernetes.io/docs/tasks/run-application/configure-pdb/Les budgets d'interruption des pods sont utilisés pour limiter le nombre d'interruptions simultanées qu'une application subira. Ils doivent être configurés pour les charges de travail s'il est important de toujours disposer d'une partie de cette charge de travail. EKS Auto Mode, Karpenter et Cluster Autoscaler connaissent et respectent les budgets d'interruption des pods configurés lors de la réduction d'échelle. EKS Auto Mode, Karpenter et Managed Node Groups respectent également les budgets d'interruption des pods lors de la mise à jour des nœuds

Évitez de faire fonctionner des Singleton Pods

Si l'ensemble de votre application s'exécute dans un seul Pod, votre application ne sera pas disponible si ce Pod est résilié. Au lieu de déployer des applications à l'aide de modules individuels, créez des déploiements. Si un pod créé par un déploiement échoue ou s'arrête, le Deployment Controller démarre un nouveau pod pour s'assurer que le nombre spécifié de pods répliques fonctionne toujours.

Exécuter plusieurs répliques

L'exécution de plusieurs pods de réplication d'une application à l'aide d'un déploiement permet à celle-ci de fonctionner de manière hautement disponible. Si un réplica échoue, les répliques restantes continueront de fonctionner, bien qu'à capacité réduite, jusqu'à ce que Kubernetes crée un autre pod pour compenser la perte. En outre, vous pouvez utiliser l'Autoscaler Horizontal Pod pour dimensionner automatiquement les répliques en fonction de la demande de charge de travail.

Planifiez des répliques sur tous les nœuds

L'exécution de plusieurs répliques ne sera pas très utile si toutes les répliques s'exécutent sur le même nœud et que le nœud devient indisponible. Envisagez d'utiliser des contraintes d'anti-affinité ou de propagation de la topologie des pods pour répartir les répliques d'un déploiement sur plusieurs nœuds de travail.

Vous pouvez encore améliorer la fiabilité d'une application classique en l'exécutant sur plusieurs zones de disponibilité.

Utilisation des règles d'anti-affinité des Pod

Le manifeste ci-dessous indique au planificateur Kubernetes de préférer placer les pods sur des nœuds et des zones de disponibilité séparés. Il ne nécessite pas de nœuds ou de zones de zone de zone de disponibilité distincts, car si c'était le cas, Kubernetes ne serait pas en mesure de planifier des pods une fois qu'un module est en cours d'exécution dans chaque zone de zone de zone de disponibilité. Si votre application ne nécessite que trois répliques, vous pouvez utiliser requiredDuringSchedulingIgnoredDuringExecution fortopologyKey: topology.kubernetes.io/zone, et le planificateur Kubernetes ne planifiera pas deux pods dans la même zone de disponibilité.

apiVersion: apps/v1 kind: Deployment metadata: name: spread-host-az labels: app: web-server spec: replicas: 4 selector: matchLabels: app: web-server template: metadata: labels: app: web-server spec: affinity: podAntiAffinity: preferredDuringSchedulingIgnoredDuringExecution: - podAffinityTerm: labelSelector: matchExpressions: - key: app operator: In values: - web-server topologyKey: topology.kubernetes.io/zone weight: 100 - podAffinityTerm: labelSelector: matchExpressions: - key: app operator: In values: - web-server topologyKey: kubernetes.io/hostname weight: 99 containers: - name: web-app image: nginx:1.16-alpine

Utilisation des contraintes d'étalement de la topologie Pod

À l'instar des règles d'anti-affinité des pods, les contraintes d'étalement de la topologie des pods vous permettent de rendre votre application disponible sur différents domaines de défaillance (ou de topologie) tels que les hôtes ou les AZ. Cette approche fonctionne très bien lorsque vous essayez de garantir la tolérance aux pannes ainsi que la disponibilité en disposant de plusieurs répliques dans chacun des différents domaines de topologie. Les règles d'anti-affinité des pods, en revanche, peuvent facilement produire un résultat où vous n'avez qu'une seule réplique dans un domaine topologique, car les pods présentant une anti-affinité les uns par rapport aux autres ont un effet répulsif. Dans de tels cas, une seule réplique sur un nœud dédié n'est pas idéale pour la tolérance aux pannes et ne constitue pas non plus une bonne utilisation des ressources. Les contraintes d'étalement de topologie vous permettent de mieux contrôler l'étalement ou la distribution que le planificateur doit essayer d'appliquer aux domaines de topologie. Voici quelques propriétés importantes à utiliser dans cette approche :

  1. Le maxSkew est utilisé pour contrôler ou déterminer le point maximum auquel les choses peuvent être inégales dans les domaines de topologie. Par exemple, si une application possède 10 répliques et est déployée sur 3 zones de zone de couverture, vous ne pouvez pas obtenir une répartition uniforme, mais vous pouvez influencer l'inégalité de la distribution. Dans ce cas, il maxSkew peut être compris entre 1 et 10. Une valeur de 1 signifie que vous pouvez potentiellement vous retrouver avec un spread similaire 4,3,3 3,3,4 à 3,4,3 ou entre les 3 AZ. En revanche, une valeur de 10 signifie que vous pouvez potentiellement vous retrouver avec un spread de l'ordre de 3 ZA 0,10,0 ou 0,0,10 sur 3 ZA. 10,0,0

  2. topologyKeyIl s'agit d'une clé pour l'une des étiquettes de nœuds et définit le type de domaine topologique qui doit être utilisé pour la distribution des pods. Par exemple, un étalement zonal comporterait la paire clé-valeur suivante :

    topologyKey: "topology.kubernetes.io/zone"
  3. La whenUnsatisfiable propriété est utilisée pour déterminer comment vous souhaitez que le planificateur réagisse si les contraintes souhaitées ne peuvent pas être satisfaites.

  4. Le labelSelector est utilisé pour trouver les pods correspondants afin que le planificateur puisse en être conscient lorsqu'il décide où placer les pods conformément aux contraintes que vous spécifiez.

En plus de ceux ci-dessus, il existe d'autres champs que vous pouvez consulter plus en détail dans la documentation de Kubernetes.

La topologie des pods répartit les contraintes sur 3 AZ

Pod topology spread constraints across 3 AZs

apiVersion: apps/v1 kind: Deployment metadata: name: spread-host-az labels: app: web-server spec: replicas: 10 selector: matchLabels: app: web-server template: metadata: labels: app: web-server spec: topologySpreadConstraints: - maxSkew: 1 topologyKey: "topology.kubernetes.io/zone" whenUnsatisfiable: ScheduleAnyway labelSelector: matchLabels: app: express-test containers: - name: web-app image: nginx:1.16-alpine

Exécuter le serveur Kubernetes Metrics

Installez le serveur de métriques Kubernetes pour vous aider à faire évoluer vos applications. Les modules complémentaires Autoscaler de Kubernetes tels que HPA et VPA doivent suivre les métriques des applications pour les faire évoluer. Le serveur de métriques collecte des métriques de ressources qui peuvent être utilisées pour prendre des décisions de dimensionnement. Les métriques sont collectées à partir de kubelets et diffusées au format Metrics API.

Le serveur de métriques ne conserve aucune donnée et n'est pas une solution de surveillance. Son objectif est d'exposer les mesures d'utilisation du processeur et de la mémoire à d'autres systèmes. Si vous souhaitez suivre l'état de votre application au fil du temps, vous avez besoin d'un outil de surveillance tel que Prometheus ou Amazon. CloudWatch

Suivez la documentation EKS pour installer metrics-server dans votre cluster EKS.

Autoscaler à dosette horizontale (HPA)

HPA peut adapter automatiquement votre application en fonction de la demande et vous aider à éviter tout impact sur vos clients pendant les pics de trafic. Il est implémenté en tant que boucle de contrôle dans Kubernetes qui interroge périodiquement les métriques des API qui fournissent des métriques de ressources.

HPA peut récupérer des métriques à partir des API suivantes : 1. metrics.k8s.ioégalement connue sous le nom d'API Resource Metrics — Fournit l'utilisation du processeur et de la mémoire pour les pods 2. custom.metrics.k8s.io — Fournit des métriques provenant d'autres collecteurs de métriques tels que Prometheus ; ces métriques sont internes à votre cluster Kubernetes. 3. external.metrics.k8s.io — Fournit des métriques externes à votre cluster Kubernetes (E.g., profondeur de la file d'attente SQS, latence ELB).

Vous devez utiliser l'une de ces trois API pour fournir la métrique permettant de faire évoluer votre application.

Dimensionnement des applications en fonction de métriques personnalisées ou externes

Vous pouvez utiliser des mesures personnalisées ou externes pour adapter votre application à des paramètres autres que l'utilisation du processeur ou de la mémoire. Les serveurs d'API Custom Metrics fournissent l'custom-metrics.k8s.ioAPI que HPA peut utiliser pour redimensionner automatiquement les applications.

Vous pouvez utiliser l'adaptateur Prometheus pour les API Kubernetes Metrics pour collecter des métriques auprès de Prometheus et les utiliser avec le HPA. Dans ce cas, l'adaptateur Prometheus exposera les métriques Prometheus au format Metrics API.

Une fois que vous avez déployé l'adaptateur Prometheus, vous pouvez interroger des métriques personnalisées à l'aide de kubectl. kubectl get —raw /apis/custom.metrics.k8s.io/v1beta1/

Les métriques externes, comme leur nom l'indique, permettent au Horizontal Pod Autoscaler de faire évoluer les déploiements à l'aide de métriques externes au cluster Kubernetes. Par exemple, dans les charges de travail de traitement par lots, il est courant de redimensionner le nombre de répliques en fonction du nombre de tâches en cours dans une file d'attente SQS.

Pour dimensionner automatiquement les charges de travail Kubernetes, vous pouvez utiliser KEDA (Kubernetes Event-driven Autoscaling), un projet open source qui peut piloter le dimensionnement des conteneurs en fonction d'un certain nombre d'événements personnalisés. Ce blog AWS explique comment utiliser Amazon Managed Service for Prometheus pour le dimensionnement automatique de la charge de travail Kubernetes.

Autoscaler à pod vertical (VPA)

Le VPA ajuste automatiquement la réservation du processeur et de la mémoire pour vos Pods afin de vous aider à « dimensionner correctement » vos applications. Pour les applications qui doivent être redimensionnées verticalement, ce qui se fait en augmentant l'allocation des ressources, vous pouvez utiliser VPA pour dimensionner automatiquement les répliques de pods ou fournir des recommandations de dimensionnement.

Votre application peut devenir temporairement indisponible si VPA doit la redimensionner, car l'implémentation actuelle de VPA n'effectue pas d'ajustements sur place sur les Pods ; au lieu de cela, elle recréera le Pod qui doit être redimensionné.

La documentation EKS inclut une procédure pas à pas pour configurer VPA.

Le projet Fairwinds Goldilocks fournit un tableau de bord permettant de visualiser les recommandations VPA pour les demandes et les limites du processeur et de la mémoire. Son mode de mise à jour VPA vous permet de redimensionner automatiquement les pods en fonction des recommandations VPA.

Mise à jour des applications

Les applications modernes nécessitent une innovation rapide avec un haut degré de stabilité et de disponibilité. Kubernetes vous fournit les outils nécessaires pour mettre à jour vos applications en permanence sans perturber vos clients.

Examinons certaines des meilleures pratiques qui permettent de déployer rapidement des modifications sans sacrifier la disponibilité.

Disposer d'un mécanisme pour effectuer des annulations

Le fait d'avoir un bouton d'annulation permet d'éviter les catastrophes. Il est recommandé de tester les déploiements dans un environnement inférieur distinct (environnement de test ou de développement) avant de mettre à jour le cluster de production. L'utilisation d'un CI/CD pipeline peut vous aider à automatiser et à tester les déploiements. Grâce à un pipeline de déploiement continu, vous pouvez rapidement revenir à l'ancienne version si la mise à niveau s'avère défectueuse.

Vous pouvez utiliser les déploiements pour mettre à jour une application en cours d'exécution. Cela se fait généralement en mettant à jour l'image du conteneur. Vous pouvez utiliser kubectl pour mettre à jour un déploiement comme suit :

kubectl --record deployment.apps/nginx-deployment set image nginx-deployment nginx=nginx:1.16.1

L'--recordargument enregistre les modifications apportées au déploiement et vous aide si vous devez effectuer une restauration. kubectl rollout history deploymentaffiche les modifications enregistrées apportées aux déploiements de votre cluster. Vous pouvez annuler une modification en utilisantkubectl rollout undo deployment <DEPLOYMENT_NAME>.

Par défaut, lorsque vous mettez à jour un déploiement qui nécessite de recréer des pods, Deployment effectue une mise à jour continue. En d'autres termes, Kubernetes ne mettra à jour qu'une partie des pods en cours d'exécution lors d'un déploiement et non tous les pods en même temps. Vous pouvez contrôler la manière dont Kubernetes effectue les mises à jour continues par le biais de propriétés. RollingUpdateStrategy

Lorsque vous effectuez une mise à jour continue d'un déploiement, vous pouvez utiliser la Max Unavailable propriété pour spécifier le nombre maximum de pods qui peuvent être indisponibles pendant la mise à jour. La Max Surge propriété de Deployment vous permet de définir le nombre maximum de Pods pouvant être créés sur le nombre de Pods souhaité.

Envisagez max unavailable de procéder à des ajustements pour vous assurer qu'un déploiement ne perturbe pas vos clients. Par exemple, Kubernetes définit 25 % max unavailable par défaut, ce qui signifie que si vous avez 100 pods, seuls 75 pods peuvent fonctionner activement lors d'un déploiement. Si votre application nécessite un minimum de 80 pods, ce déploiement peut être perturbateur. Au lieu de cela, vous pouvez le régler max unavailable à 20 % pour vous assurer qu'il y aura au moins 80 pods fonctionnels tout au long du déploiement.

Utilisez les blue/green déploiements

Les changements sont intrinsèquement risqués, mais ceux qui ne peuvent pas être annulés peuvent être potentiellement catastrophiques. Les procédures de modification qui vous permettent de revenir efficacement dans le temps grâce à une restauration rendent les améliorations et les expérimentations plus sûres. Blue/green les déploiements vous offrent une méthode pour annuler rapidement les modifications en cas de problème. Dans cette stratégie de déploiement, vous créez un environnement pour la nouvelle version. Cet environnement est identique à la version actuelle de l'application en cours de mise à jour. Une fois le nouvel environnement configuré, le trafic est acheminé vers le nouvel environnement. Si la nouvelle version produit les résultats souhaités sans générer d'erreur, l'ancien environnement est supprimé. Dans le cas contraire, le trafic est rétabli à l'ancienne version.

Vous pouvez effectuer blue/green des déploiements dans Kubernetes en créant un nouveau déploiement identique au déploiement de la version existante. Une fois que vous avez vérifié que les pods du nouveau déploiement fonctionnent sans erreur, vous pouvez commencer à envoyer du trafic vers le nouveau déploiement en modifiant les selector spécifications du service qui achemine le trafic vers les pods de votre application.

De nombreux outils d'intégration continue tels que Flux, Jenkins et Spinnaker vous permettent d'automatiser les déploiements. blue/green Le blog AWS Containers inclut une présentation détaillée d'AWS Load Balancer Controller : Utilisation d'AWS Load Balancer Controller pour le blue/green déploiement, le déploiement Canary et les tests A/B

Utilisez les déploiements Canary

Les déploiements Canary sont une variante des blue/green déploiements qui permet d'éliminer de manière significative les risques liés aux modifications. Dans cette stratégie de déploiement, vous créez un nouveau déploiement avec moins de pods en plus de votre ancien déploiement, et vous redirigez un faible pourcentage du trafic vers le nouveau déploiement. Si les statistiques indiquent que la nouvelle version fonctionne aussi bien ou mieux que la version existante, vous augmentez progressivement le trafic vers le nouveau déploiement tout en le faisant évoluer jusqu'à ce que tout le trafic soit redirigé vers le nouveau déploiement. En cas de problème, vous pouvez acheminer tout le trafic vers l'ancien déploiement et arrêter d'envoyer du trafic vers le nouveau déploiement.

Bien que Kubernetes ne propose aucune méthode native pour effectuer des déploiements Canary, vous pouvez utiliser des outils tels que Flagger avec Istio. https://docs.flagger.app/tutorials/istio-progressive-delivery

Bilans de santé et auto-guérison

Aucun logiciel n'est exempt de bogues, mais Kubernetes peut vous aider à minimiser l'impact des défaillances logicielles. Dans le passé, si une application tombait en panne, quelqu'un devait remédier à la situation en redémarrant l'application manuellement. Kubernetes vous permet de détecter les défaillances logicielles dans vos Pods et de les remplacer automatiquement par de nouvelles répliques. Kubernetes vous permet de surveiller l'état de santé de vos applications et de remplacer automatiquement les instances défectueuses.

Kubernetes prend en charge trois types de bilans de santé : https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-startup-probes/

  1. Sonde Liveness

  2. Sonde de démarrage (prise en charge dans la version 1.16+ de Kubernetes)

  3. Sonde de préparation

Kubelet, l'agent Kubernetes, est responsable de l'exécution de toutes les vérifications susmentionnées. Kubelet peut vérifier l'état d'un pod de trois manières : kubelet peut soit exécuter une commande shell dans le conteneur d'un pod, soit envoyer une requête HTTP GET à son conteneur, soit ouvrir un socket TCP sur un port spécifié.

Si vous choisissez une sonde exec basée, qui exécute un script shell dans un conteneur, assurez-vous que la commande shell se ferme avant l'expiration de la timeoutSeconds valeur. Dans le cas contraire, votre nœud sera soumis à des <defunct> processus, ce qui entraînera une défaillance du nœud.

Recommandations

Utilisez Liveness Probe pour éliminer les gousses malsaines

La sonde Liveness peut détecter les blocages dans lesquels le processus continue de s'exécuter, mais où l'application ne répond plus. Par exemple, si vous utilisez un service Web qui écoute sur le port 80, vous pouvez configurer une sonde Liveness pour envoyer une requête HTTP GET sur le port 80 du Pod. Kubelet envoie périodiquement une requête GET au Pod et attend une réponse ; si le Pod répond entre 200 et 399, le Kubelet considère que le Pod est en bonne santé ; sinon, le Pod sera marqué comme étant en mauvais état. Si les contrôles de santé d'un Pod échouent continuellement, le kubelet y mettra fin.

Vous pouvez l'utiliser initialDelaySeconds pour retarder la première sonde.

Lorsque vous utilisez la Liveness Probe, assurez-vous que votre application ne se retrouve pas dans une situation dans laquelle tous les Pods échouent simultanément à la Liveness Probe, car Kubernetes essaiera de remplacer tous vos Pods, ce qui mettra votre application hors ligne. En outre, Kubernetes continuera à créer de nouveaux pods qui échoueront également aux sondes Liveness Probes, ce qui exercera une pression inutile sur le plan de contrôle. Évitez de configurer la sonde Liveness pour qu'elle dépende d'un facteur externe à votre Pod, par exemple une base de données externe. En d'autres termes, une base de données externe à votre POD qui ne répond pas ne devrait pas faire échouer vos Pods à leurs sondes Liveness.

L'article de Sandor Szücs intitulé LIVENESS PROBES ARE DANGEROUS décrit les problèmes qui peuvent être causés par des sondes mal configurées.

Utilisez Startup Probe pour les applications qui mettent plus de temps à démarrer

Lorsque votre application a besoin de plus de temps pour démarrer, vous pouvez utiliser la sonde de démarrage pour retarder la sonde de réactivité et de préparation. Par exemple, une application Java qui a besoin d'hydrater le cache d'une base de données peut prendre jusqu'à deux minutes avant d'être pleinement fonctionnelle. Toute sonde de vivacité ou de préparation peut échouer avant qu'elle ne soit pleinement fonctionnelle. La configuration d'une sonde de démarrage permettra à l'application Java de se rétablir avant l'exécution de Liveness ou Readiness Probe.

Jusqu'à ce que la sonde de démarrage réussisse, toutes les autres sondes sont désactivées. Vous pouvez définir la durée maximale que Kubernetes doit attendre avant le démarrage de l'application. Si, après la durée maximale configurée, le Pod ne démarre toujours pas avec les sondes de démarrage, il sera arrêté et un nouveau Pod sera créé.

La sonde de démarrage est similaire à la sonde Liveness : en cas d'échec, le Pod est recréé. Comme l'explique Ricardo A. dans son article Fantastic Probes And How To Configure Them, les sondes de démarrage doivent être utilisées lorsque le démarrage d'une application est imprévisible. Si vous savez que votre application a besoin de dix secondes pour démarrer, vous devriez initialDelaySeconds plutôt utiliser Liveness/Readiness Probe with.

Utilisez Readiness Probe pour détecter une indisponibilité partielle

Alors que la sonde Liveness détecte les défaillances d'une application qui sont résolues en arrêtant le Pod (donc en redémarrant l'application), la sonde Readiness Probe détecte les situations dans lesquelles l'application peut être temporairement indisponible. Dans ces situations, l'application peut temporairement ne plus répondre ; toutefois, elle devrait redevenir saine une fois cette opération terminée.

Par exemple, lors d' I/O opérations intensives sur disque, les applications peuvent être temporairement indisponibles pour traiter les demandes. Dans ce cas, mettre fin au Pod de l'application n'est pas une solution ; dans le même temps, les demandes supplémentaires envoyées au Pod peuvent échouer.

Vous pouvez utiliser la Readiness Probe pour détecter une indisponibilité temporaire dans votre application et arrêter d'envoyer des requêtes à son Pod jusqu'à ce qu'il redevienne fonctionnel. Contrairement à Liveness Probe, où une panne entraînerait une recréation du Pod, une sonde de préparation défaillante signifierait que le Pod ne recevra aucun trafic en provenance de Kubernetes Service. Lorsque la Readiness Probe réussit, le Pod recommence à recevoir du trafic en provenance du Service.

Tout comme pour la Liveness Probe, évitez de configurer des sondes de préparation qui dépendent d'une ressource externe au Pod (telle qu'une base de données). Voici un scénario dans lequel un Readiness mal configuré peut rendre l'application non fonctionnelle : si la sonde de préparation d'un pod échoue alors que la base de données de l'application est inaccessible, les autres répliques de pod échoueront également simultanément car elles partagent les mêmes critères de contrôle de santé. En configurant la sonde de cette manière, chaque fois que la base de données n'est pas disponible, les sondes de préparation du pod échoueront et Kubernetes cessera d'envoyer du trafic à tous les pods.

L'utilisation des sondes de préparation a pour effet secondaire d'augmenter le temps nécessaire à la mise à jour des déploiements. Les nouvelles répliques ne recevront pas de trafic à moins que les Readiness Probes ne soient efficaces ; d'ici là, les anciennes répliques continueront de recevoir du trafic.

Faire face aux perturbations

Les pods ont une durée de vie limitée. Même si vous avez des pods qui fonctionnent depuis longtemps, il est prudent de s'assurer que les pods se terminent correctement le moment venu. Selon votre stratégie de mise à niveau, les mises à niveau des clusters Kubernetes peuvent nécessiter la création de nouveaux nœuds de travail, ce qui nécessite que tous les pods soient recréés sur des nœuds plus récents. Une gestion appropriée des terminaisons et des budgets d'interruption des modules peuvent vous aider à éviter les interruptions de service, car les pods sont supprimés des anciens nœuds et recréés sur les nouveaux nœuds.

La méthode préférée pour mettre à niveau les nœuds de travail consiste à créer de nouveaux nœuds de travail et à mettre fin aux anciens. Avant de terminer les nœuds de travail, vous devriez le drain faire. Lorsqu'un nœud de travail est vidé, tous ses modules sont expulsés en toute sécurité. La sécurité est un mot clé à cet égard ; lorsque les cabines d'un travailleur sont expulsées, elles ne reçoivent pas simplement un SIGKILL signal. Au lieu de cela, un SIGTERM signal est envoyé au processus principal (PID 1) de chaque conteneur des Pods expulsés. Une fois le SIGTERM signal envoyé, Kubernetes accorde au processus un certain temps (délai de grâce) avant qu'un SIGKILL signal ne soit envoyé. Ce délai de grâce est de 30 secondes par défaut ; vous pouvez remplacer le délai par défaut en utilisant grace-period flag dans kubectl ou declare terminationGracePeriodSeconds dans votre Podspec.

kubectl delete pod <pod name> —grace-period=<seconds>

Il est courant d'avoir des conteneurs dans lesquels le processus principal n'a pas de PID 1. Considérez ce contenant Python-based d'échantillon :

$ kubectl exec python-app -it ps PID USER TIME COMMAND 1 root 0:00 {script.sh} /bin/sh ./script.sh 5 root 0:00 python app.py

Dans cet exemple, le script shell reçoitSIGTERM, le processus principal, qui se trouve être une application Python dans cet exemple, ne reçoit aucun SIGTERM signal. Lorsque le Pod est arrêté, l'application Python sera supprimée brusquement. Il est possible de remédier à ce problème en modifiant le ENTRYPOINT conteneur pour lancer l'application Python. Vous pouvez également utiliser un outil tel que dumb-init pour vous assurer que votre application peut gérer les signaux.

Vous pouvez également utiliser les hooks de conteneur pour exécuter un script ou une requête HTTP au démarrage ou à l'arrêt du conteneur. L'action de PreStop crochet s'exécute avant que le conteneur ne reçoive un SIGTERM signal et doit être terminée avant que ce signal ne soit envoyé. La terminationGracePeriodSeconds valeur s'applique à partir du moment où l'action PreStop hook commence à s'exécuter, et non au moment où le SIGTERM signal est envoyé.

Recommandations

Protégez la charge de travail critique grâce à Pod Disruption Budgets

Pod Disruption Budget ou PDB peuvent suspendre temporairement le processus d'expulsion si le nombre de répliques d'une application tombe en dessous du seuil déclaré. Le processus d'expulsion se poursuivra une fois que le nombre de répliques disponibles dépassera le seuil. Vous pouvez utiliser PDB pour déclarer le maxUnavailable nombre minAvailable et le nombre de répliques. Par exemple, si vous souhaitez qu'au moins trois copies de votre application soient disponibles, vous pouvez créer un PDB.

apiVersion: policy/v1beta1 kind: PodDisruptionBudget metadata: name: my-svc-pdb spec: minAvailable: 3 selector: matchLabels: app: my-svc

La politique PDB ci-dessus indique à Kubernetes d'arrêter le processus d'expulsion jusqu'à ce que trois répliques ou plus soient disponibles. Respecte PodDisruptionBudgets le drainage des nœuds. Lors de la mise à niveau d'un groupe de nœuds géré par EKS, les nœuds sont vidés avec un délai de 15 minutes. Au bout de quinze minutes, si la mise à jour n'est pas forcée (l'option est appelée Mise à jour continue dans la console EKS), la mise à jour échoue. Si la mise à jour est forcée, les pods sont supprimés.

Pour les nœuds autogérés, vous pouvez également utiliser des outils tels que AWS Node Termination Handler, qui garantit que le plan de contrôle de Kubernetes répond de manière appropriée aux événements susceptibles de rendre votre instance EC2 indisponible, tels que les événements de maintenance EC2 et les interruptions ponctuelles d'EC2. https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/spot-interruptions.html Il utilise l'API Kubernetes pour boucler le nœud afin de s'assurer qu'aucun nouveau pod n'est programmé, puis le vide, mettant fin à tous les pods en cours d'exécution.

Vous pouvez utiliser l'anti-affinité des pods pour planifier les pods d'un déploiement sur différents nœuds et éviter les retards liés à la PDB lors des mises à niveau des nœuds.

Pratiquez l'ingénierie du chaos

L'ingénierie du chaos est la discipline qui consiste à expérimenter sur un système distribué afin de renforcer la confiance dans la capacité du système à résister à des conditions de production turbulentes.

Dans son blog, Dominik Tornow explique que Kubernetes est un système déclaratif dans lequel «  l'utilisateur fournit une représentation de l'état souhaité du système au système. Le système considère ensuite l'état actuel et l'état souhaité pour déterminer la séquence de commandes permettant de passer de l'état actuel à l'état souhaité. » Cela signifie que Kubernetes stocke toujours l'état souhaité et que si le système s'écarte, Kubernetes prendra des mesures pour rétablir l'état. Par exemple, si un nœud de travail devient indisponible, Kubernetes replanifiera les pods sur un autre nœud de travail. De même, en cas de replica panne, le contrôleur de déploiement en créera un nouveaureplica. De cette manière, les contrôleurs Kubernetes corrigent automatiquement les défaillances.

Les outils d'ingénierie du chaos tels que Gremlin vous aident à tester la résilience de votre cluster Kubernetes et à identifier les points de défaillance uniques. Les outils qui introduisent un chaos artificiel dans votre cluster (et au-delà) peuvent révéler les faiblesses systémiques, permettre d'identifier les goulots d'étranglement et les mauvaises configurations, et de corriger les problèmes dans un environnement contrôlé. La philosophie de Chaos Engineering préconise de casser les choses à dessein et de tester l'infrastructure afin de minimiser les temps d'arrêt imprévus.

Utiliser un Service Mesh

Vous pouvez utiliser un maillage de services pour améliorer la résilience de votre application. Les maillages de services permettent la communication de service à service et améliorent l'observabilité de votre réseau de microservices. La plupart des produits de maillage de services fonctionnent en faisant fonctionner un petit proxy réseau parallèlement à chaque service qui intercepte et inspecte le trafic réseau de l'application. Vous pouvez placer votre application dans un maillage sans modifier votre application. Grâce aux fonctionnalités intégrées du service proxy, vous pouvez lui demander de générer des statistiques réseau, de créer des journaux d'accès et d'ajouter des en-têtes HTTP aux demandes sortantes pour le traçage distribué.

Un maillage de services peut vous aider à rendre vos microservices plus résilients grâce à des fonctionnalités telles que les nouvelles tentatives automatiques de demande, les délais d'attente, l'interruption des circuits et la limitation du débit.

Si vous gérez plusieurs clusters, vous pouvez utiliser un maillage de services pour activer la communication service à service entre clusters.

Maillages de service

Observabilité

L'observabilité est un terme générique qui inclut la surveillance, la journalisation et le traçage. Les applications basées sur des microservices sont distribuées par nature. Contrairement aux applications monolithiques où la surveillance d'un seul système est suffisante, dans une architecture d'application distribuée, vous devez surveiller les performances de chaque composant. Vous pouvez utiliser des systèmes de surveillance, de journalisation et de traçage distribué au niveau du cluster pour identifier les problèmes dans votre cluster avant qu'ils ne perturbent vos clients.

Les outils intégrés de Kubernetes pour le dépannage et la surveillance sont limités. Le serveur de métriques collecte les métriques des ressources et les stocke en mémoire mais ne les conserve pas. Vous pouvez consulter les journaux d'un pod à l'aide de kubectl, mais Kubernetes ne conserve pas automatiquement les journaux. Et la mise en œuvre du traçage distribué se fait soit au niveau du code de l'application, soit à l'aide de maillages de services.

L'extensibilité de Kubernetes brille ici. Kubernetes vous permet d'apporter votre solution centralisée de surveillance, de journalisation et de traçage préférée.

Recommandations

Surveillez vos applications

Le nombre de métriques que vous devez surveiller dans les applications modernes ne cesse de croître. Il est utile de disposer d'un moyen automatisé de suivre vos demandes afin de pouvoir vous concentrer sur la résolution des problèmes de vos clients. Cluster-wide des outils de surveillance tels que Prometheus ou CloudWatch Container Insights peuvent surveiller votre cluster et votre charge de travail et vous fournir des signaux quand, ou de préférence, avant que les choses ne tournent mal.

Les outils de surveillance vous permettent de créer des alertes auxquelles votre équipe des opérations peut s'abonner. Envisagez des règles pour activer des alarmes en cas d'événements qui, s'ils sont exacerbés, peuvent entraîner une panne ou affecter les performances de l'application.

Si vous ne savez pas quels indicateurs vous devez surveiller, vous pouvez vous inspirer des méthodes suivantes :

  • Méthode RED. Représente les demandes, les erreurs et la durée.

  • Méthode USE. Représente l'utilisation, la saturation et les erreurs.

L'article de Sysdig sur les meilleures pratiques en matière d'alerte sur Kubernetes inclut une liste complète des composants qui peuvent avoir un impact sur la disponibilité de vos applications.

Utiliser la bibliothèque cliente Prometheus pour exposer les métriques de l'application

Outre la surveillance de l'état de l'application et l'agrégation de métriques standard, vous pouvez également utiliser la bibliothèque cliente Prometheus pour exposer des métriques personnalisées spécifiques à l'application afin d'améliorer son observabilité.

Utilisez des outils de journalisation centralisés pour collecter et conserver les journaux

La journalisation dans EKS se divise en deux catégories : les journaux du plan de contrôle et les journaux des applications. La journalisation du plan de contrôle EKS fournit des journaux d'audit et de diagnostic directement depuis le plan de contrôle vers CloudWatch les journaux de votre compte. Les journaux des applications sont des journaux produits par les Pods qui s'exécutent au sein de votre cluster. Les journaux d'applications incluent les journaux produits par les pods qui exécutent les applications de logique métier et les composants du système Kubernetes tels que CoreDNS, Cluster Autoscaler, Prometheus, etc.

EKS fournit cinq types de journaux de plan de contrôle  :

  1. Journaux des composants du serveur d'API Kubernetes

  2. Audit

  3. Authentificateur

  4. Gestionnaire de contrôleur

  5. Planificateur

Les journaux du gestionnaire de contrôleurs et du planificateur peuvent aider à diagnostiquer les problèmes du plan de contrôle tels que les goulots d'étranglement et les erreurs. Par défaut, les journaux du plan de contrôle EKS ne sont pas envoyés à CloudWatch Logs. Vous pouvez activer la journalisation du plan de contrôle et sélectionner les types de journaux du plan de contrôle EKS que vous souhaitez capturer pour chaque cluster de votre compte

La collecte des journaux des applications nécessite l'installation d'un outil d'agrégation de journaux tel que Fluent Bit, Fluentd ou CloudWatch Container Insights dans votre cluster.

Les outils d'agrégation de journaux Kubernetes s'exécutent en tant que journaux de conteneurs DaemonSets et extraient les journaux des conteneurs depuis les nœuds. Les journaux des applications sont ensuite envoyés vers une destination centralisée à des fins de stockage. Par exemple, CloudWatch Container Insights peut utiliser Fluent Bit ou Fluentd pour collecter les journaux et les envoyer à CloudWatch Logs pour stockage. Fluent Bit et Fluentd prennent en charge de nombreux systèmes d'analyse de journaux populaires tels qu'Elasticsearch et InfluxDB, ce qui vous permet de modifier le backend de stockage de vos journaux en modifiant Fluentbit ou la configuration des journaux de Fluentd.

Utilisez un système de traçage distribué pour identifier les goulots d'étranglement

Une application moderne typique comporte des composants répartis sur le réseau et sa fiabilité dépend du bon fonctionnement de chacun des composants qui composent l'application. Vous pouvez utiliser une solution de traçage distribuée pour comprendre comment les demandes circulent et comment les systèmes communiquent. Les traces peuvent vous indiquer où se trouvent les goulots d'étranglement de votre réseau d'applications et prévenir les problèmes susceptibles de provoquer des défaillances en cascade.

Deux options s'offrent à vous pour implémenter le traçage dans vos applications : vous pouvez soit implémenter le traçage distribué au niveau du code à l'aide de bibliothèques partagées, soit utiliser un maillage de services.

La mise en œuvre du traçage au niveau du code peut être désavantageuse. Dans cette méthode, vous devez apporter des modifications à votre code. Cela est encore plus compliqué si vous avez des applications polyglottes. Vous êtes également responsable de la maintenance d'une autre bibliothèque, dans l'ensemble de vos services.

Les maillages de service tels que LinkerD et Istio peuvent être utilisés pour implémenter le traçage distribué dans votre application en modifiant le moins possible le code de l'application. Vous pouvez utiliser Service Mesh pour normaliser la génération, la journalisation et le suivi des métriques.

Les outils de traçage tels qu'AWS X-Ray et Jaeger prennent en charge à la fois les implémentations de bibliothèques partagées et de maillage de services.

Envisagez d'utiliser un outil de traçage tel qu'AWS X-Ray ou Jaeger qui prend en charge les deux implémentations (bibliothèque partagée et service mesh) afin de ne pas avoir à changer d'outil si vous adoptez ultérieurement le service mesh.