Résoudre les problèmes de synchronisation des configurations avec votre cluster

Cette page explique comment résoudre les problèmes de synchronisation des configurations avec votre cluster.

Résoudre les erreurs KNV 2009

Les erreurs KNV2009 indiquent que Config Sync n'a pas réussi à synchroniser certaines configurations avec le cluster. Les sections suivantes expliquent certaines des causes les plus courantes et indiquent comment les résoudre.

Opération interdite sur certaines ressources

Étant donné que vous devez attribuer leur contrôle RBAC aux objets RepoSync, il se peut que vous ne disposiez pas des autorisations nécessaires pour appliquer des ressources.

Vous pouvez vérifier que les autorisations manquent en obtenant l'état de la ressource RepoSync :

kubectl get reposync repo-sync -n NAMESPACE -o yaml

Remplacez NAMESPACE par l'espace de noms dans lequel vous avez créé votre dépôt d'espaces de noms.

Vous pouvez également exécuter la commande nomos status :

Si les messages suivants apparaissent dans l'état, cela signifie que le rapprochement dans NAMESPACE ne dispose pas de l'autorisation nécessaire pour appliquer la ressource :

KNV2009: deployments.apps "nginx-deployment" is forbidden: User "system:serviceaccount:config-management-system:ns-reconciler-default" cannot get resource "deployments" in API group "apps" in the namespace "default"

Pour résoudre ce problème, vous devez déclarer une configuration RoleBinding qui accorde au compte de service l'autorisation de gérer la ressource défaillante dans cet espace de noms. Des informations sur l'ajout d'un objet RoleBinding sont incluses dans la section Configurer la synchronisation à partir de plusieurs dépôts.

Ce problème peut également affecter les objets RootSync si vous avez utilisé spec.override.roleRefs pour modifier les rôles attribués à l'objet RootSync. Si vous n'avez pas défini ce champ, les objets RootSync se voient attribuer le rôle cluster-admin par défaut.

L'objet ResourceGroup dépasse la limite de taille d'objet etcd.

Si vous recevez l'erreur suivante lorsqu'un rapprochement tente d'appliquer des configurations au cluster, l'objet ResourceGroup dépasse la limite de taille d'objet etcd :

KNV2009: too many declared resources causing ResourceGroup.kpt.dev, config-management-system/root-sync failed to be applied: task failed (action: "Inventory", name: "inventory-add-0"): Request entity too large: limit is 3145728. To fix, split the resources into multiple repositories.

Nous vous recommandons de diviser votre dépôt Git en plusieurs dépôts. Si vous ne parvenez pas à scinder le dépôt Git, car l'objet est déjà trop volumineux et les modifications ne sont pas conservées, vous pouvez limiter le problème en configurant RootSync ou RepoSync pour désactiver temporairement l'écriture de l'état d'objet dans ResourceGroup. Pour ce faire, définissez le champ .spec.override.statusMode de l'objet RootSync ou RepoSync sur disabled. Ainsi, Config Sync cesse de mettre à jour l'état des ressources gérées dans l'objet ResourceGroup. Cette action réduit la taille de l'objet ResourceGroup. Cependant, vous ne pouvez pas afficher l'état des ressources gérées à partir de nomos status ou de gcloud alpha anthos config sync.

Si vous ne voyez aucune erreur dans l'objet RootSync ou RepoSync, cela signifie que les objets de votre source de vérité ont été synchronisés avec le cluster. Pour vérifier si la ressource ResourceGroup dépasse la limite de taille d'objet etcd, vérifiez à la fois l'état de la ressource ResourceGroup et le journal du contrôleur ResourceGroup :

  1. Vérifiez l'état de ResourceGroup:

    • Pour vérifier l'objet RootSync, exécutez la commande suivante :

      kubectl get resourcegroup root-sync -n config-management-system
      
    • Pour vérifier l'objet RepoSync, exécutez la commande suivante :

      kubectl get resourcegroup repo-sync -n NAMESPACE
      

      Remplacez NAMESPACE par l'espace de noms dans lequel vous avez créé votre dépôt d'espaces de noms.

    Le résultat ressemble à celui de l'exemple ci-dessous.

    NAME        RECONCILING   STALLED   AGE
    root-sync   True          False     35m
    

    Si la valeur de la colonne RECONCILING est True, cela signifie que la ressource ResourceGroup est encore rapprochée.

  2. Consultez les journaux du contrôleur ResourceGroup:

    kubectl logs deployment resource-group-controller-manager -c manager -n resource-group-system
    

    Si une erreur semblable à l'exemple suivant s'affiche dans le résultat, la ressource ResourceGroup est trop volumineuse et dépasse la limite de taille d'objet etcd :

    "error":"etcdserver: request is too large"
    

Pour empêcher le ResourceGroup de devenir trop volumineux, réduisez le nombre de ressources de votre dépôt Git. Vous pouvez diviser un dépôt racine en plusieurs dépôts racines.

Dépendance appliquée avant expiration du rapprochement

Si vous synchronisez des objets avec des dépendances, vous pouvez recevoir une erreur semblable à l'exemple suivant lorsque le rapprochement tente d'appliquer des objets avec l'annotation config.kubernetes.io/depends-on au cluster :

KNV2009: skipped apply of Pod, bookstore/pod4: dependency apply reconcile timeout: bookstore_pod3__Pod  For more information, see https://g.co/cloud/acm-errors#knv2009

Cette erreur signifie que l'objet de dépendance n'a pas rapproché le délai de rapprochement par défaut de 5 minutes. Config Sync ne peut pas appliquer l'objet dépendant, car avec l'annotation config.kubernetes.io/depends-on, Config Sync n'applique que les objets dans l'ordre souhaité. Vous pouvez ignorer le délai de rapprochement par défaut en définissant spec.override.reconcileTimeout.

Il est également possible que la dépendance se réconcilie une fois la tentative de synchronisation initiale terminée. Dans ce cas, la dépendance doit être détectée comme rapprochée lors de la prochaine tentative de synchronisation, ce qui débloque l'application des dépendances. Dans ce cas, l'erreur peut être signalée brièvement, puis supprimée. Prolonger le délai d'expiration de la mise à jour peut éviter que l'erreur ne soit signalée de manière intermittente.

Les informations sur l'inventaire sont "nil"

Si vous recevez l'erreur suivante lorsque le rapprochement tente d'appliquer des configurations au cluster, il est probable que votre inventaire ne dispose d'aucune ressource ou que le fichier manifeste comporte une annotation non gérée :

KNV2009: inventory info is nil\n\nFor more information, see https://g.co/cloud/acm-errors#knv2009

Essayez les solutions suivantes pour résoudre ce problème :

  1. Évitez de configurer des synchronisations où toutes les ressources comportent l'annotation configmanagement.gke.io/managed: disabled, en vous assurant qu'au moins une ressource est gérée par Config Sync.
  2. Ajoutez l'annotation configmanagement.gke.io/managed: disabled uniquement après avoir terminé une synchronisation initiale de la ressource sans cette annotation.

Plusieurs modèles d'objets d'inventaire

Si vous recevez l'erreur suivante lorsque le rapprochement tente d'appliquer des configurations au cluster, il est probable que vous disposiez d'une configuration d'inventaire générée par kpt dans la source de vérité, par exemple un dépôt Git :

KNV2009: Package has multiple inventory object templates.  The package should have one and only one inventory object template.   For more information, see https://g.co/cloud/acm-errors#knv2009

Le problème se produit car Config Sync gère sa propre configuration d'inventaire. Pour résoudre ce problème, supprimez la configuration d'inventaire de votre source de vérité.

Impossible de modifier des champs immuables

Vous ne pouvez pas modifier un champ immuable dans une configuration en modifiant la valeur de la source de vérité. Toute tentative de modification entraîne une erreur semblable à celle-ci :

KNV2009: failed to apply RESOURCE: admission webhook "deny-immutable-field-updates.cnrm.cloud.google.com" denied the request: cannot make changes to immutable field(s):

Si vous devez mettre à jour un champ immuable, supprimez manuellement l'objet dans le cluster. Config Sync peut ensuite recréer l'objet avec la nouvelle valeur de champ.

Échec de la détection de l'API

Si un message d'erreur semblable à celui-ci s'affiche, vous rencontrez peut-être une erreur de découverte d'API :

KNV2002: API discovery failed: APIServer error: unable to retrieve the complete list of server APIs: external.metrics.k8s.io/v1beta1: received empty response for: external.metrics.k8s.io/v1beta1

Config Sync utilise la découverte de l'API Kubernetes pour rechercher les ressources compatibles avec le cluster. Cela permet à Config Sync de valider les types de ressources spécifiés dans votre source et de surveiller ces ressources pour détecter les modifications apportées au cluster.

Avant la version 1.28 de Kubernetes, chaque fois qu'un backend APIService n'était pas opérationnel ou renvoyait un résultat de liste vide, la découverte d'API échouait, ce qui entraînait une erreur de Config Sync et de plusieurs autres composants Kubernetes. De nombreux services backend APIService courants ne sont pas hautement disponibles. Cela peut donc arriver relativement souvent, simplement en mettant à jour le backend ou en le reprogrammant sur un autre nœud.

metrics-server et custom-metrics-stackdriver-adapter sont des exemples de backends APIService avec une seule instance dupliquée. Certains backends APIService renvoient toujours des résultats de liste vides, comme custom-metrics-stackdriver-adapter. Les webhooks non opérationnels sont une autre cause courante d'échec de la découverte d'API.

Après la version 1.28 de Kubernetes, avec la fonctionnalité de découverte agrégée activée, un backend APIService non opérationnel n'entraîne plus d'erreurs non gérées. Au lieu de cela, le groupe de ressources géré par cette APIService est indiqué comme ne disposant d'aucune ressource. Cela permet de poursuivre la synchronisation tant que la ressource non opérationnelle n'est pas spécifiée dans votre source.

Autoréparation différée

L'autoréparation surveille les ressources gérées, détecte la dérive de la source de vérité et l'annule.

L'autoréparation est suspendue pendant la tentative de synchronisation. Ce comportement signifie que l'autoréparation peut être retardée, en particulier si des erreurs de synchronisation empêchent le rapprochement. Pour réactiver l'autoréparation, corrigez toutes les erreurs de synchronisation signalées.

Nombre élevé de requêtes d'API Kubernetes

Config Sync utilise une stratégie à plusieurs instances pour effectuer le scaling et l'isolation des locataires et des domaines de défaillance. De ce fait, chaque RootSync et RepoSync obtient sa propre instance de rapprochement. En plus de se synchroniser chaque fois que des modifications sont apportées à la source, chaque instance de rapprochement se synchronise également périodiquement dans le cadre de son comportement d'autoréparation, pour annuler toutes les modifications manquées par la correction de dérive active. Lorsque vous ajoutez des objets RootSync ou RepoSync, cela entraîne une augmentation linéaire du nombre de requêtes API effectuées par les rapprochements synchronisant les ressources avec Kubernetes. Ainsi, si vous avez de nombreux objets RootSync et RepoSync, cela peut parfois entraîner une charge de trafic importante sur l'API Kubernetes.

Pour effectuer la synchronisation, Config Sync utilise l'application côté serveur. Cette méthode remplace le flux de requête GET et PATCH normal par une seule requête PATCH, ce qui réduit le nombre total d'appels d'API, mais augmente le nombre d'appels PATCH. Cela garantit que les modifications apportées sont correctes, même lorsque la version du groupe de ressources dans la source ne correspond pas à la version par défaut du groupe de ressources du cluster. Toutefois, vous pouvez voir des requêtes PATCH dans le journal d'audit, même en l'absence de modification de la source ou de dérive par rapport à l'état souhaité. Ceci est normal, mais peut être surprenant.

En cas d'erreur de la synchronisation, une nouvelle tentative est effectuée jusqu'à ce qu'elle aboutisse. Toutefois, si cela nécessite une interaction humaine, Config Sync peut générer des erreurs et des nouvelles tentatives pendant un certain temps, ce qui augmente le nombre de requêtes adressées à l'API Kubernetes. Les tentatives s'arrêtent de manière exponentielle, mais si de nombreux objets RootSync ou RepoSync ne parviennent pas à se synchroniser simultanément, cela peut entraîner une charge de trafic importante sur l'API Kubernetes.

Pour résoudre ces problèmes, essayez l'une des options suivantes :

  • Corrigez rapidement les erreurs de configuration afin qu'elles ne s'accumulent pas.
  • Combinez plusieurs objets RootSync ou RepoSync pour réduire le nombre de rapprochements effectuant des requêtes API Kubernetes.

Désinstallation de KubeVirt bloquée par les finaliseurs

KubeVirt est un package Kubernetes qui utilise plusieurs finaliseurs, nécessitant un ordre de suppression précis pour faciliter le nettoyage. Si les objets KubeVirt sont supprimés dans le mauvais ordre, la suppression d'autres objets KubeVirt peut se bloquer ou cesser de répondre indéfiniment.

Si vous avez essayé de désinstaller KubeVirt et qu'il a été bloqué, suivez les instructions pour supprimer manuellement KubeVirt.

Pour résoudre ce problème à l'avenir, déclarez les dépendances entre les objets de ressources afin de vous assurer qu'ils sont supprimés dans l'ordre inverse des dépendances.

Suppression d'objets bloquée par les finaliseurs

Les finaliseurs Kubernetes sont des entrées de métadonnées qui indiquent à Kubernetes de ne pas autoriser la suppression d'un objet tant qu'un contrôleur spécifique n'a pas effectué de nettoyage. Cela peut entraîner l'échec de la synchronisation ou de la mise à jour, si les conditions de nettoyage ne sont pas remplies ou si le contrôleur qui effectue le nettoyage de cette ressource n'est pas opérationnel ou a été supprimé.

Pour atténuer ce problème, identifiez la ressource en cours de finalisation et le contrôleur qui doit effectuer le nettoyage.

Si le contrôleur n'est pas opérationnel, la résolution de la cause première devrait permettre le nettoyage des ressources et le blocage de la suppression de l'objet.

Si le contrôleur est opérationnel, il doit avoir appliqué une condition d'état à l'objet supprimé pour expliquer pourquoi le nettoyage s'est bloqué. Si ce n'est pas le cas, consultez les journaux du contrôleur pour obtenir des indications sur la cause première.

Le fait de bloquer la suppression d'un objet indique souvent que les objets ont été supprimés dans le mauvais ordre. Pour éviter ce type de problème à l'avenir, déclarez les dépendances entre les objets de ressources afin de vous assurer qu'ils sont supprimés en remontant dans l'ordre des dépendances.

Les champs ResourceGroup continuent de changer

Lors d'une tentative de synchronisation, l'inventaire est mis à jour pour définir l'état des ressources sur "En attente". En cas d'échec de la synchronisation, l'inventaire est mis à jour pour remplacer l'état des ressources par Échec. Lorsque la synchronisation est relancée après un échec, ce schéma se répète, ce qui entraîne des mises à jour périodiques de l'inventaire. Le nombre de resourceVersion de ResourceGroup augmente alors à chaque mise à jour, et l'état de synchronisation oscille. Ceci est normal, mais peut être surprenant.

Un échec de synchronisation peut être dû à un certain nombre de problèmes. L'une des plus courantes est celle des autorisations insuffisantes pour gérer les ressources spécifiées dans la source. Pour corriger cette erreur, ajoutez les objets RoleBinding ou ClusterRoleBinding appropriés afin d'accorder au rapprochement RepoSync ou RootSync l'autorisation de gérer les ressources qui ne parviennent pas à se synchroniser.

L'application côté serveur ne supprime ou ne rétablit pas les champs non spécifiés dans la source.

Config Sync utilise l'application côté serveur pour appliquer les fichiers manifestes de la source à Kubernetes. Cette opération est nécessaire pour permettre à d'autres contrôleurs de gérer les champs metadata et spec. L'autoscaler horizontal de pods est un exemple de ce cas de figure, qui met à jour le nombre d'instances dupliquées dans un déploiement. Par conséquent, Config Sync ne gère que les champs spécifiés dans le fichier manifeste source. Cela a pour effet secondaire que lors de l'adoption des objets ressources existants, les champs non spécifiés dans la source ne sont pas modifiés, ce qui peut parfois rendre la configuration fusionnée non valide ou incorrecte.

Pour éviter ce problème lors de l'adoption d'une ressource, utilisez exactement les mêmes champs dans la source lors de l'adoption initiale, puis modifiez les champs de la source après la synchronisation, afin que Config Sync supprime correctement les champs qu'il a précédemment appliqués et les remplace par les nouveaux champs de la source. Pour éviter ce problème, vous pouvez également supprimer la ressource du cluster et autoriser Config Sync à appliquer la nouvelle version.

Étapes suivantes