Saltar al contenido

¿Cómo soluciono los problemas de programación de pods relacionados con la disponibilidad de los nodos en Amazon EKS?

16 minutos de lectura
0

Tengo problemas o errores de disponibilidad de nodos cuando intento programar mis pods de trabajo de Amazon Elastic Kubernetes Service (Amazon EKS). Mis pods están bloqueados en estado Pendiente.

Solución

Nota: Si se muestran errores al ejecutar comandos de la Interfaz de la línea de comandos de AWS (AWS CLI), consulta Solución de problemas de AWS CLI. Además, asegúrate de utilizar la versión más reciente de la AWS CLI.

Errores de memoria o CPU insuficientes

Recibes los siguientes mensajes de error cuando la CPU o la memoria disponibles en los nodos de trabajo no son suficientes para que el pod alcance el estado de ejecución:

  • "Warning FailedScheduling 16m default-scheduler 0/2 nodes are available: 1 Too many pods, 2 Insufficient cpu, 2 Insufficient memory. preemption: 0/2 nodes are available: 2 No preemption victims found for incoming pod"
  • "Warning FailedScheduling 11m default-scheduler 0/2 nodes are available: 1 Insufficient cpu, 1 Insufficient memory, 1 node(s) were unschedulable. preemption: 0/2 nodes are available: 1 No preemption victims found for incoming pod, 1 Preemption is not helpful for scheduling"

Para resolver problemas de memoria o CPU insuficientes, sigue estos pasos:

  1. Inicia una sesión SSH del Administrador de sesiones (una función de AWS Systems Manager) con tus nodos de trabajo.

  2. Ejecuta el siguiente comando kubectl top node para obtener el porcentaje actual de uso de CPU y memoria de cada nodo:

    kubectl top node

    Nota: Para obtener más información sobre el comando anterior, consulta kubectl top node en el sitio web de Kubernetes.

  3. Ejecuta el siguiente comando kubectl describe para obtener información sobre el total de recursos disponibles en tu nodo:

    kubectl describe node your_node_name

    Nota: Sustituye your_node_name por el nombre de tu nodo. Para obtener más información sobre el comando anterior, consulta kubectl describe en el sitio web de Kubernetes.
    El siguiente ejemplo de salida muestra los recursos de un nodo que puedes asignar a un pod:

    Allocatable:
      cpu: 1930m
      ephemeral-storage: 18242267924
      hugepages-1Gi: 0
      hugepages-2Mi: 0
      memory: 3388304Ki
      pods: 17
  4. Identifica la clase de instancia de Amazon Elastic Compute Cloud (Amazon EC2) que utilizan tus nodos de trabajo. Luego, revisa la CPU y la memoria predeterminadas que están disponibles en las instancias.

  5. Revisa los límites de recursos y las solicitudes que definiste en el despliegue. Para obtener más información, consulta Deployments (Despliegues) en el sitio web de Kubernetes. Si configuras los límites, asegúrate de que cumplan con tus requisitos de carga de trabajo. El siguiente ejemplo de salida muestra los límites y las solicitudes de recursos:

    Limits:
      memory: 170Mi
    Requests:
      cpu: 100m
      memory: 70Mi

    Nota: Los valores correctos para los límites y las solicitudes pueden ayudarte a determinar si debes escalar verticalmente la capacidad de tus nodos de trabajo. Para obtener más información, consulta Administración de recursos para pods y contenedores en el sitio web de Kubernetes.

Problemas de cuota de interfaz de red

Recibes el siguiente mensaje de error cuando alcanzas la cuota de la interfaz de red elástica en tu nodo:

"Warning FailedScheduling 117s default-scheduler 0/2 nodes are available: 1 Too many pods. preemption: 0/2 nodes are available: 2 No preemption victims found for incoming pod"

Nota: Cada pod de un clúster de Kubernetes tiene su propia dirección IP. La cantidad de direcciones IP que admite un tipo de instancia ayuda a determinar la cantidad máxima de pods en ejecución en un nodo de trabajo. Si alcanzas el número máximo de pods que se pueden ejecutar en un nodo de trabajo, es posible que tus pods se queden en estado Pendiente.

Para comprobar la cantidad máxima de pods que se pueden ejecutar en cada nodo, ejecuta el siguiente comando describe-instance-types:

aws ec2 describe-instance-types --filters "Name=instance-type,Values=c5.*" --query "InstanceTypes[].{ Type: InstanceType, MaxENI: NetworkInfo.MaximumNetworkInterfaces, IPv4addr: NetworkInfo.Ipv4AddressesPerInterface}" --output table

El resultado del comando muestra información sobre la cantidad máxima de interfaces de red y direcciones IPv4 por interfaz para cada tipo de instancia. El resultado del comando anterior muestra un pod menos que el número máximo de pods porque el resultado excluye la primera interfaz de red (eth0).

Para obtener más información, consulta el número máximo de pods recomendado por Amazon EKS para cada tipo de instancia de Amazon EC2. Consulta también Número máximo de direcciones IP por interfaz de red.

Para obtener información sobre la cantidad máxima de pods que puede admitir una instancia, consulta amazon-vpc-cni-k8s en el sitio web de GitHub.

Si las direcciones IP disponibles en tus instancias de nodo de trabajo actuales no son suficientes, toma las siguientes medidas:

  • Escala verticalmente la clase de instancia a una que admita más pods. Se recomienda comprobar las cuotas de la interfaz de red antes de realizar el escalamiento vertical.
  • Usa Karpenter y el escalador automático de clústeres para escalar horizontalmente el recuento de nodos.

Errores de tolerancia o taint

Recibes el siguiente mensaje de error cuando hay un problema con los taints o las tolerancias:

"Warning FailedScheduling 12s default-scheduler 0/2 nodes are available: 2 node(s) had untolerated taint {NodeType: MemoryOptimized}. preemption: 0/2 nodes are available: 2 Preemption is not helpful for scheduling"

El pod que quieres programar requiere un nodo con un taint específico (NodeType: MemoryOptimized). Sin embargo, la programación falla porque el nodo no está disponible en tu clúster.

Para resolver problemas relacionados con los taints o las tolerancias, sigue estos pasos:

  1. Ejecuta el siguiente comando kubectl describe para obtener los taints que configuraste en tu nodo:

    kubectl describe node your_node_name

    Nota: Sustituye your_node_name por el nombre de tu nodo. Puedes programar un pod en el nodo solo cuando el pod tenga una tolerancia coincidente.

  2. Ejecuta el siguiente comando kubectl describe para obtener las tolerancias de un pod:

    kubectl describe pod your_pod_name -n your_namespace

    Nota: Sustituye your_pod_name por el nombre de tu pod y your_namespace por tu espacio de nombres.

Errores de afinidad

Recibes el siguiente mensaje de error cuando tienes un problema con la afinidad de un nodo:

"Warning FailedScheduling 13s default-scheduler 0/2 nodes are available: 2 node(s) didn't match Pod's node affinity/selector. preemption: 0/2 nodes are available: 2 Preemption is not helpful for scheduling"

Para resolver los problemas de afinidad, sigue estos pasos:

  1. Actualiza la configuración de afinidad de nodos del pod para usar preferredDuringSchedulingIgnoredDuringExecution en lugar de requiredDuringSchedulingIgnoredDuringExecution.

    Nota: Para programar un pod, debes usar requiredDuringSchedulingIgnoredDuringExecution. El programador de Kubernetes programa el pod solo en un nodo que cumpla con la regla de afinidad.

  2. Agrega nodos a tu clúster que tengan la afinidad correspondiente para que el programador de Kubernetes pueda encontrar un nodo para programar el pod.

  3. Elimina los términos del selector de nodos del despliegue o actualiza el grupo de nodos a un valor que cumpla la condición del despliegue. Elige la opción adecuada en función de tus requisitos y de la disponibilidad de los nodos en tu clúster de Kubernetes.

    El siguiente ejemplo de salida muestra una configuración de selector de nodos en un despliegue:

    affinity:
      nodeAffinity:
         requiredDuringSchedulingIgnoredDuringExecution:
            nodeSelectorTerms:
              - matchExpressions:
                - key: instance-az
                  operator: In
                  values:
                   - az1
                  - az2
  4. Ejecuta el siguiente comando kubectl describe para obtener los detalles del nodo:

    kubectl describe node your_node_name

    Nota: Sustituye your_node_name por el nombre de tu nodo.

    El siguiente ejemplo muestra los detalles del nodo:

    Name: ip-10-1-1-172.ap-south-1.compute.internal
    Roles: <none>
    Labels: beta.kubernetes.io/arch=amd64
                 beta.kubernetes.io/instance-type=t3.medium
                 beta.kubernetes.io/os=linux
                 instance-az=az1

Nota: El valor clave que definiste en el despliegue debe estar en tu nodo para que Kubernetes pueda colocar el pod en el nodo.

Errores en el grupo de seguridad del pod

Recibes el siguiente mensaje de error cuando hay problemas con los grupos de seguridad de tus pods:

"Warning FailedScheduling 3s default-scheduler 0/3 nodes are available: 1 Insufficient vpc.amazonaws.com/pod-eni, 2 node(s) had untolerated taint {eks.amazonaws.com/compute-type: fargate}. preemption: 0/3 nodes are available: 1 No preemption victims found for incoming Pod, 2 Preemption is not helpful for scheduling"

Nota: Cuando usas grupos de seguridad para los pods en Amazon EKS, el controlador de recursos de la VPC crea una interfaz de red de ramificaciones para cada pod. El controlador de recursos de la VPC también crea una interfaz de red troncal en el nodo de trabajo para administrar la interfaz de red de la ramificación.

Importante: Para usar los grupos de seguridad del pod, debes iniciar tus nodos de trabajo en los tipos de instancias de Nitro, como las familias C5, M5, R5 y T3. Los tipos de instancia de Nitro admiten la funcionalidad de interfaz de red necesaria para adaptarse a la interfaz de red de ramificaciones para los pods.

Para resolver el problema del grupo de seguridad del pod, sigue estos pasos:

  1. Ejecuta el siguiente comando kubectl describe para confirmar que tu instancia de nodo de trabajo admite una interfaz troncal:

    kubectl describe node your_node_name

    Nota: Sustituye your_node_name por el nombre de tu nodo.

  2. En la descripción del nodo que aparece en el resultado del comando anterior, comprueba los eventos del controlador de recursos de la VPC.
    El siguiente resultado muestra un ejemplo de una instancia incompatible:

    Events:
      Type     Reason                   Age                    From                             Message
      ----     ------                   ----                   ----                             -------
      Normal   RegisteredNode           22m                    node-controller                  Node ip-192-168-59-29.us-east-2.compute.internal event: Registered Node ip-192-168-59-29.us-east-2.compute.internal in Controller
      Normal   ControllerVersionNotice  21m                    vpc-resource-controller          The node is managed by VPC resource controller version v1.4.9
      Normal   NodeReady                21m                    kubelet                          Node ip-192-168-59-29.us-east-2.compute.internal status is now: NodeReady
      Warning  Unsupported              13m (x16 over 21m)     vpc-resource-controller          The instance type t3.small is not supported for trunk interface (Security Group for Pods)
    

Errores de soporte de pods de Fargate

Recibes el siguiente mensaje de error cuando AWS Fargate no admite tu pod:

"Warning FailedScheduling <unknown> fargate-scheduler Pod not supported on Fargate: volumes not supported: mysql-db not supported because: PVC mysql-db not bound"

Los pods que se ejecutan en Fargate y utilizan un volumen de Amazon Elastic File System (Amazon EFS) tienen los mismos requisitos que los pods normales. Fargate no programa un pod cuando los recursos de PersistentVolume y PersistentVolumeClaim necesarios no están en el clúster.

Para resolver el problema de fargate, sigue estos pasos:

  1. Crea y configura correctamente los recursos de PersistentVolume y PersistentVolumeClaim necesarios en el clúster. Para obtener más información, consulta Configure a Pod to use a PersistentVolume for storage (Configuración de un pod para usar un PersistentVolume para el almacenamiento) en el sitio web de Kubernetes.
  2. Comprueba si hay problemas con tus recursos de PersistentVolume y PersistentVolumeClaim cuando el volumen está enlazado al pod. Por ejemplo, es posible que tengas problemas con el sistema de archivos EFS, los permisos u otros problemas de configuración.

Soporte de Fargate para errores de tipo de volumen

Aparece el siguiente mensaje de error cuando el pod contiene una definición para un tipo de volumen no compatible:

"Warning FailedScheduling <unknown> fargate-scheduler Pod not supported on Fargate: volumes not supported: admin-panel is of an unsupported volume Type"

Importante: No puedes montar volúmenes de Amazon Elastic Block Store (Amazon EBS) en pods de Fargate.

Para resolver el problema del tipo de volumen no compatible, lleva a cabo las siguientes acciones:

  • Asegúrate de que la definición del pod especifique un volumen de EFS y no un volumen de EBS ni otro tipo de volumen no compatible.
  • Comprueba que has configurado correctamente los recursos de PersistentVolume y PersistentVolumeClaim y que hacen referencia a un sistema de archivos EFS.
  • Comprueba si hay problemas en el sistema de archivos EFS, los permisos o la configuración que puedan provocar que el volumen no se conecte al pod.

Contexto de seguridad sobre los errores de Fargate

Aparece el siguiente mensaje de error cuando un contexto de seguridad no es válido:

"Warning FailedScheduling 109s fargate-scheduler Pod not supported on Fargate: invalid SecurityContext fields: Privileged"

Para resolver el problema del contexto de seguridad, asegúrate de que tus pods de Fargate cumplan con los siguientes requisitos:

  • La definición del pod no puede especificar el contexto de seguridad del contenedor con privilegios. Fargate no acepta contenedores con privilegios.
  • La definición del pod no puede montar el sistema de archivos raíz del host (/) en el contenedor. Fargate aísla los contenedores del sistema de archivos raíz del host.

Errores del programador incorrecto en Fargate

Si usas Amazon EKS con perfiles de Fargate o programadores personalizados, es posible que no tengas el programador de Kubernetes correcto para administrar tus pods.

Para resolver los problemas del programador, sigue estos pasos:

  1. Revisa los eventos del pod.
    En el siguiente ejemplo se muestra que el programador predeterminado no puede encontrar un nodo para el pod porque hay un taint asociado al tipo de computación de Fargate:

    Events:
    Type     Reason            Age        From               Message
    ----     ------            ----       ----               -------
    Warning  FailedScheduling  109s       default-scheduler  0/2 nodes are available: 2 node(s) had untolerated taint {eks.amazonaws.com/compute-type: fargate}. preemption: 0/2 nodes are available: 2 Preemption is not helpful for scheduling..

    Nota: fargate-scheduler debe programar los pods de Fargate.

  2. Ejecuta el siguiente comando kubectl get mutatingwebhookconfigurations para comprobar que has instalado el webhook de Fargate en el clúster:

    kubectl get mutatingwebhookconfigurations 0500-amazon-eks-fargate-mutation.amazonaws.com

Si el resultado muestra la configuración de webhooks y fargate-scheduler no puede captar el pod, comprueba si hay otras configuraciones de webhooks mutantes personalizadas que puedan entrar en conflicto. Por ejemplo, un webhook conflictivo puede causar el problema porque Fargate procesa los webhooks en orden alfabético.

Errores de conflictos de puertos

Recibes el siguiente mensaje de error cuando hay un conflicto de puertos en la máquina host en la que el programador de Kubernetes programa el pod:

"Warning FailedScheduling 10s default-scheduler 0/2 nodes are available: 1 node(s) didn't have free ports for requested pod ports. 1 node(s) didn't match the requested hostname"

El error se produce porque configuraste varios pods con el mismo valor de hostPort o porque otro proceso de la máquina host ya está ejecutando el puerto.

Cuando configuras un pod con hostNetwork: true, los contenedores que se ejecutan dentro del pod tienen acceso directo a las interfaces de red de la máquina host. Como resultado, los puertos del contenedor están expuestos directamente a la red externa en los puertos host correspondientes.

Para resolver los problemas de conflictos de puertos, sigue estos pasos:

  1. Ejecuta el siguiente comando kubectl describe para comprobar las configuraciones de los puertos:

    kubectl describe deploy nginx-deployment

    El siguiente ejemplo de salida muestra dónde está la información del puerto:

        spec:
          hostNetwork: true
          containers:
          - name: nginx
            image: nginx:latest
            ports:
            - containerPort: 80
              hostPort: 80
  2. Modifica la red o el puerto del host. Por ejemplo, puedes establecer hostNetwork en el valor predeterminado false para asignar una interfaz de red virtual al pod. También puedes actualizar la configuración del pod para usar otro puerto host que no esté ya en uso en la máquina host. Para permitir que el kernel asigne automáticamente un puerto de host aleatorio a tus pods, establece hostPort en 0 como en el siguiente ejemplo:

      Containers:
       nginx:
        Image:        nginx:latest
        Port:         80/TCP
        Host Port:    0/TCP
  3. Programa el pod en otro host. Si el conflicto de puertos es específico de la máquina host en la que quieres programar el pod, programa el pod en otro nodo. El nodo debe estar en tu clúster de Kubernetes. También puedes usar la lógica de afinidad. Para obtener más información, consulta Cómo colocar pods de Kubernetes en Amazon EKS mediante la afinidad, los taints y las tolerancias de nodos.

Errores de afinidad de nodos conflictivos

Recibes el siguiente mensaje de error cuando tienes reglas de afinidad de nodos en conflicto:

"Warning FailedScheduling 57s (x3 over 3m3s) default-scheduler 0/15 nodes are available: 1 node(s) were unschedulable, 14 node(s) had volume node affinity conflict"

Este error se produce cuando los requisitos de volumen del pod no se cumplen para los nodos disponibles debido a reglas de afinidad de nodos en conflicto.

Para resolver el problema de afinidad de nodos en conflicto, sigue estos pasos:

  1. Identifica las reglas de afinidad de nodos en conflicto en tus definiciones de volumen y pod. Por ejemplo, es posible que tu pod tenga una regla de afinidad de nodos que requiera la etiqueta node-type=high-storage, pero el volumen requiere la etiqueta node-type=ssd-storage.

  2. Para resolver el conflicto de reglas, actualiza las reglas de afinidad de nodos para el pod o el volumen. Por ejemplo, actualiza la regla de afinidad de nodos del pod para que coincida con los requisitos del volumen, como en el siguiente ejemplo:

    affinity:
      nodeAffinity:
        requiredDuringSchedulingIgnoredDuringExecution:
          nodeSelectorTerms:
          - matchExpressions:
            - key: node-type
              operator: In
              values:
              - ssd-storage
  3. Confirma que las etiquetas de tus nodos coinciden con tus reglas de afinidad. Luego, verifica que los nodos disponibles en tu clúster tengan las etiquetas correctas para cumplir con los nuevos requisitos. Para enumerar los nodos y sus etiquetas, ejecuta el siguiente comando kubectl get nodes:

    kubectl get nodes --show-labels

    Nota: Asegúrate de tener nodos disponibles con la etiqueta node-type=ssd-storage requerida.

  4. Modifica tus grupos de nodos o agrega nuevos grupos de nodos. Si utilizas grupos de nodos y los nodos no tienen las etiquetas necesarias, actualiza los grupos de nodos existentes. O bien, crea nuevos grupos de nodos con las etiquetas y los tipos de instancia adecuados.

No hay errores de zona de volumen disponibles

Recibes los siguientes mensajes de error cuando intentas implementar un pod en tu clúster y no tienes una zona de volumen disponible:

  • "Warning FailedScheduling 60s (x5 over 60s) default-scheduler Pod has unbound PersistentVolumeClaims (repeated 2 times)"
  • "Warning FailedScheduling 2s (x16 over 59s) default-scheduler 0/2 nodes are available: 2 node(s) had no available volume zone"

Los requisitos de volumen del pod no se cumplen porque las zonas de volumen disponibles y las restricciones de zonas de volumen del pod no coinciden.

Para resolver este problema de zona de volumen, sigue estos pasos:

  1. Revisa las definiciones de volumen y pod para identificar las restricciones específicas de la zona de volumen que causan el problema con la zona de volumen. Por ejemplo, comprueba si configuraste tu pod o volumen para usar una zona de disponibilidad en la que no ejecutes nodos de trabajo.

  2. Ejecuta el siguiente comando kubectl get pv para comprobar qué zonas de volumen están disponibles en tu clúster:

    kubectl get pv --all-namespaces -o jsonpath='{range .items[*]}{.spec.awsElasticBlockStore.availabilityZone}{"\n"}{end}' | sort | uniq

    Nota: Asegúrate de que la lista de salida incluya las zonas de volumen que tu pod o volumen requieren.

  3. Actualiza las restricciones de la zona de volumen. Si la zona de volumen requerida no está disponible, actualiza la configuración del volumen o del pod. La configuración debe restringir la creación de volúmenes solo a las zonas de disponibilidad en las que se ejecutan los nodos de trabajo.

  4. Confirma que los grupos de nodos abarcan varias zonas de disponibilidad. Si tus grupos de nodos no abarcan varias zonas, crea nuevos grupos de nodos que incluyan las zonas de volumen requeridas.

OFICIAL DE AWSActualizada hace un año