Protección de nodos (versión preliminar) en Azure Kubernetes Service (AKS)

Node Hardening es una función opcional para grupos de nodos de Linux que protege la estabilidad del nodo cuando las cargas de trabajo someten a los nodos a presión de CPU, memoria o disco. Al habilitar La protección de nodos en un clúster, AKS cambia la forma en que cada nodo reserva y aplica recursos para los componentes de Kubernetes y los servicios del host, y cómo el kubelet expulsa los pods cuando los recursos escasean.

En este artículo se explica qué cambios realiza Node Hardening, compara los valores predeterminados protegidos con los valores predeterminados estándar de AKS y muestra cómo habilitar, comprobar, personalizar y deshabilitar la característica.

Importante

Las características en versión preliminar de AKS están disponibles en régimen de autoservicio y mediante adhesión voluntaria. Las versiones preliminares se proporcionan "tal cual" y "como están disponibles", y están excluidas de los Acuerdos de nivel de servicio y la garantía limitada. Las versiones preliminares de AKS cuentan con soporte parcial por parte del servicio al cliente en la medida de lo posible. Por lo tanto, estas características no están diseñadas para su uso en producción. Para más información, consulte los siguientes artículos de soporte:

Ventajas del fortalecimiento de nodos

En nodos ocupados o de ráfaga, las cargas de trabajo pueden consumir recursos que necesitan el kubelet, el entorno de ejecución del contenedor y los servicios de host. Cuando esto sucede, los nodos pueden dejar de responder, informar de un estado NotReady o finalizar los pods abruptamente. La protección de nodos reduce estos riesgos de las siguientes maneras:

  • Reservas forzadas: De forma predeterminada, AKS usa valores de kube-reserved solo para calcular la capacidad que el programador puede asignar a los pods. Mediante el refuerzo de nodos, el kubelet también aplica la capacidad kube-reserved y system-reserved a través de grupos de control de Linux (cgroups). El kubelet y containerd se ejecutan en un grupo cgroup dedicado kubereserved.slice, por lo que mantienen su recurso compartido de CPU reservado y memoria incluso cuando los pods saturan el nodo.
  • Capacidad dedicada para los servicios del host: El refuerzo de nodos agrega una asignación reservada del sistema para los servicios del sistema operativo del host, que se ejecutan en system.slice.
  • Más margen de memoria: El umbral estricto de expulsión para la memoria disponible se ajusta en función de la memoria del nodo, por lo que el kubelet expulsa los pods antes de que al nodo le quede muy poca memoria.
  • Desalojo ordenado: Los umbrales de desalojo flexibles permiten al kubelet desalojar los pods de forma ordenada, con un período de gracia de terminación, cuando la memoria o el espacio en disco se agotan. El desalojo forzoso, que finaliza inmediatamente los pods, actúa como último recurso.
  • Reservas en función de la densidad de pods: El cálculo de la memoria reservada para kube aumenta en función del número máximo de pods por nodo, lo que tiene en cuenta la sobrecarga de kubelet y containerd de ejecutar más pods.

¿Qué cambia al habilitar Node Hardening?

En las tablas siguientes se comparan los valores predeterminados estándar para los nodos de Linux que ejecutan Kubernetes 1.29 o versiones posteriores con los valores predeterminados que AKS aplica cuando se habilita la protección de nodos.

Reservas de recursos

Setting Sin endurecimiento de nodos Con endurecimiento de Node
CPU reservada para Kube En función del número de núcleos de CPU. Para más información, consulte Reservas de CPU. Sin cambios
Memoria reservada de Kube min(20 × maxPods + 50, 25% of node memory) MiB min(35 × maxPods + max(250, 2% of node memory), 25% of node memory) MiB
Identificadores de proceso reservados de Kube (PID) 1000 No reservado
CPU reservada por el sistema None 100m
Memoria reservada del sistema None 200 MiB, además de 100 MiB para cada 32 GiB completo de memoria de nodo, además de 100 MiB para clústeres que usan Azure CNI
Almacenamiento efímero reservado por el sistema None 1Gi

Umbrales de desalojo

Setting Sin Node Hardening Con refuerzo de Node
Desalojo forzado: memory.available 100Mi 250Mi para nodos con 8 GiB de memoria o menos, 375Mi para nodos con más de 8 GiB y menos de 32 GiB, y 512Mi para nodos con 32 GiB o más
Desalojo forzoso: nodefs.available y nodefs.inodesFree 10% y 5% Sin cambios
Desalojo forzoso: pid.available 2000 No establecido
Desalojo suave: memory.available None 500Mi, 750Mi, o 1Gi, con los mismos niveles de memoria de nodo que el desalojo forzoso, con un período de gracia de 30 segundos
Desalojo suave: nodefs.available y nodefs.inodesFree None 12% y 7%, cada una con un período de gracia de 2 minutos
Período máximo de gracia de finalización del pod durante el desalojo no forzoso No establecido 60 segundos

Aplicación de cgroups

Setting Sin endurecimiento de nodos Con refuerzo de la seguridad de nodos
Asignable del nodo forzado pods pods, kube-reserved y system-reserved
Kubelet y cgroup de containerd system.slice, sin límites kubereserved.slice, con memoria limitada a la memoria kube-reserved y un recurso compartido de CPU proporcional a la CPU kube-reserved
cgroup de servicios del host system.slice, sin límites system.slice, con memoria limitada a la memoria reservada por el sistema y una cuota de CPU proporcional a la CPU reservada por el sistema

Dado que Node Hardening reserva más capacidad, los nodos notifican menos capacidad asignable para los pods. Por ejemplo, en un nodo con 4 vCPU y 16 GiB de memoria que usa Azure CNI, al habilitar el endurecimiento de nodos se reduce la capacidad asignable de la siguiente manera:

  • Con el máximo predeterminado de 250 pods por nodo, unos 570 MiB de memoria más, 100 millicores de CPU y 1 GiB de almacenamiento efímero.
  • Con un máximo de 30 pods por nodo, limitado a aproximadamente 1,3 GiB de memoria, 100 millicores de CPU y 1 GiB de almacenamiento efímero.

Los umbrales de desalojo no estrictos no reducen la capacidad asignable. Solo cambian cuando el kubelet comienza a expulsar pods.

Considerations

Tenga en cuenta las siguientes consideraciones antes de habilitar Node Hardening:

  • Habilita la protección de nodos en el nivel de clúster y se aplica a todos los grupos de nodos de Linux del clúster. No se puede habilitar para grupos de nodos individuales y no afecta a Windows grupos de nodos.
  • Los nodos notifican una capacidad asignable menor, por lo que es posible que los pods que caben en un nodo antes de habilitar Node Hardening no se ajusten después. Revise las solicitudes de recursos de pod y los tamaños del grupo de nodos.
  • Los servicios de host en system.slice comparten un límite de memoria dura igual a la memoria reservada del sistema. Si ejecuta sus propios agentes en nodos como servicios de systemd, como seguridad, supervisión o agentes de reenvío de registros, esos agentes se contabilizan en este límite. Valide el uso de memoria y la estabilidad antes de usar Node Hardening en producción.
  • Los valores establecidos en la configuración de kubelet personalizada de un grupo de nodos anulan los valores predeterminados correspondientes de Node Hardening. Para obtener más información, consulte Personalizar la configuración de protección de nodos.
  • Si deshabilita Node Hardening más adelante, los grupos de nodos existentes mantienen la configuración reforzada de expulsión temporal, incluso después de que se les reinstale la imagen a sus nodos. Para quitar esta configuración, debe crear nuevos grupos de nodos. Para obtener más información, consulte Deshabilitar la protección de nodos.
  • Los valores predeterminados pueden cambiar mientras la característica está en versión preliminar. Comience con un clúster que no sea de producción y valide las cargas de trabajo en condiciones representativas de presión de nodo.

Prerequisites

  • Una suscripción a Azure. Si no tiene una, cree una cuenta gratuita.
  • Un clúster de AKS con grupos de nodos de Linux o permisos para crear uno.
  • La aks-preview extensión de CLI de Azure y la CustomNodeConfigPreview marca de función, como se describe en las secciones siguientes.

Instalación de la extensión aks-preview CLI de Azure

  1. Instale la aks-preview extensión mediante el az extension add comando .

    az extension add --name aks-preview
    
  2. Actualice a la versión más reciente de la extensión mediante el az extension update comando .

    az extension update --name aks-preview
    

Registro de la marca de característica CustomNodeConfigPreview

  1. Registre el indicador de función CustomNodeConfigPreview con el comando az feature register.

    az feature register --namespace "Microsoft.ContainerService" --name "CustomNodeConfigPreview"
    

    Tarda unos minutos en que el estado muestre Registrado.

  2. Compruebe el estado del registro mediante el az feature show comando .

    az feature show --namespace "Microsoft.ContainerService" --name "CustomNodeConfigPreview"
    
  3. Cuando el estado muestre Registrado, actualice la inscripción del proveedor de recursos Microsoft.ContainerService mediante el comando az provider register.

    az provider register --namespace "Microsoft.ContainerService"
    

Activar la protección de nodos

En la versión preliminar, Node Hardening no está habilitado de forma predeterminada.

Habilitar la protección de nodos en un clúster nuevo

Cree un clúster con Node Hardening habilitado mediante el comando az aks create con el parámetro --enable-node-hardening.

Este comando requiere la extensión aks-preview y el indicador de característica CustomNodeConfigPreview. Para obtener más información, consulte Requisitos previos.

az aks create \
    --resource-group <resource-group-name> \
    --name <cluster-name> \
    --enable-node-hardening \
    --generate-ssh-keys

Para confirmar el cambio, consulte Verificar la configuración de protección del nodo.

Habilitar la protección de nodos en un clúster existente

Habilite La protección de nodos en un clúster existente mediante el az aks update comando con el --enable-node-hardening parámetro .

Este comando requiere la extensión aks-preview y el indicador de función CustomNodeConfigPreview. Para obtener más información, consulte Requisitos previos.

az aks update \
    --resource-group <resource-group-name> \
    --name <cluster-name> \
    --enable-node-hardening

Para confirmar el cambio, consulte Verificar la configuración de protección de nodos.

Verificar la configuración de hardening de nodos

  1. Obtenga las credenciales del clúster mediante el comando az aks get-credentials.

    az aks get-credentials --resource-group <resource-group-name> --name <cluster-name>
    
  2. Revise la configuración efectiva de reserva y desalojo de kubelet en un nodo consultando el punto de conexión de configuración de kubelet.

    kubectl get --raw "/api/v1/nodes/<node-name>/proxy/configz" | jq '.kubeletconfig | {kubeReserved, systemReserved, evictionHard, evictionSoft, evictionSoftGracePeriod, evictionMaxPodGracePeriod, enforceNodeAllocatable}'
    

    En un nodo protegido, systemReserved y evictionSoft contienen valores, e enforceNodeAllocatable incluye kube-reserved y system-reserved.

  3. Compare la capacidad del nodo con sus recursos asignables.

    kubectl get node <node-name> -o jsonpath='{.status.capacity}{"\n"}{.status.allocatable}{"\n"}'
    

    En un nodo protegido, la CPU, la memoria y el almacenamiento efímero asignables son inferiores a la capacidad. La diferencia es igual a los valores de kube-reserved y system-reserved en Reservas de recursos, además de los umbrales de expulsión duros en Umbrales de expulsión. Por ejemplo, en un nodo con 4 vCPU y 16 GiB de memoria que usa Azure CNI, la CPU asignable es 240 millicores inferior a la capacidad: 140 millicores de CPU reservada para kube y 100 millicores de CPU reservada por el sistema.

Personalizar la configuración de protección de nodos

Puede anular los valores predeterminados de kube-reserved y de expulsión de un grupo de nodos Linux mediante una configuración personalizada de kubelet. Esta configuración requiere el indicador de función CustomNodeConfigPreview. Puede usarlos tanto si el endurecimiento de nodos está habilitado en el clúster como si no. AKS administra los valores reservados por el sistema y la aplicación de cgroup, y no puedes personalizarlos.

Cada configuración sobrescribe una fila en las tablas Reservas de recursos o Umbrales de expulsión. Las filas reservadas de Kube corresponden a las configuraciones de kubeReserved. Las filas de expulsión dura corresponden a las configuraciones de hardEvictionThreshold. Las filas de desalojo suave corresponden a las opciones softEvictionThreshold y softEvictionGracePeriod. El período máximo de gracia de terminación del pod corresponde a evictionMaxPodGracePeriodInSeconds.

Puede configurar las siguientes opciones:

Setting Overrides Description
kubeReserved.cpuMillicores CPU reservada para Kube CPU reservada para demonios del sistema de Kubernetes, en millicores.
kubeReserved.memoryMB Memoria reservada de Kube Memoria reservada para demonios del sistema de Kubernetes, en MiB.
hardEvictionThreshold.memoryAvailable Expulsión forzada: memory.available Umbral de desalojo estricto para la memoria disponible.
hardEvictionThreshold.nodeFsAvailable Desalojo forzoso: nodefs.available Umbral de expulsión duro para el espacio disponible del sistema de archivos de nodo.
hardEvictionThreshold.nodeFsInodesFree Desalojo forzado: nodefs.inodesFree Umbral de expulsión duro para inodos libres del sistema de archivos del nodo.
softEvictionThreshold.memoryAvailable Desalojo no forzoso: memory.available Umbral de desalojo no forzoso para la memoria disponible.
softEvictionThreshold.nodeFsAvailable Expulsión no forzada: nodefs.available Umbral de expulsión suave para el espacio disponible del sistema de archivos del nodo.
softEvictionThreshold.nodeFsInodesFree Desalojo no forzoso: nodefs.inodesFree Umbral de expulsión suave para inodes libres del sistema de archivos del nodo.
softEvictionGracePeriod.memoryAvailable Desalojo suave: memory.available período de gracia Cuánto tiempo debe permanecer la memoria disponible por debajo de su umbral flexible antes de que kubelet expulse los pods.
softEvictionGracePeriod.nodeFsAvailable Desalojo no forzoso: nodefs.available período de gracia Cuánto espacio de sistema de archivos de nodo disponible debe permanecer por debajo de su umbral flexible antes de que kubelet expulse los pods.
softEvictionGracePeriod.nodeFsInodesFree Desalojo flexible: nodefs.inodesFree período de gracia Cuánto tiempo los inodos libres del sistema de archivos del nodo deben permanecer por debajo de su umbral flexible antes de que el kubelet expulse pods.
evictionMaxPodGracePeriodInSeconds Período máximo de gracia de finalización del pod durante el desalojo suave Número máximo de segundos que kubelet permite que los pods finalicen durante un desalojo suave.
  • Para conocer los valores permitidos, los mínimos y las reglas de validación para cada configuración, consulte Parámetros de configuración de nodos personalizados para AKS.
  • Para cada señal de expulsión, establezca el umbral de desalojo flexible y su período de gracia coincidente y asegúrese de que cada umbral de desalojo flexible sea mayor que el umbral de desalojo estricto para la misma señal.
  1. Cree un archivo de configuración de kubelet, como nodehardening-kubelet.json, con la configuración que desea personalizar. En el ejemplo siguiente se establecen todos los valores configurables. Establece kube-reserved en 200 millicores de CPU y 1024 MiB de memoria. Establece umbrales de expulsión duros de 512Mi de la memoria disponible, 10% del espacio disponible del sistema de archivos y 5% de inodos libres. Establece umbrales de expulsión temporal de 1Gi, 12%y 7% con períodos de gracia de 30 segundos, 2 minutos y 2 minutos. También establece un período de gracia de terminación de pod máximo de 60 segundos.

    {
      "kubeReserved": {
        "cpuMillicores": 200,
        "memoryMB": 1024
      },
      "hardEvictionThreshold": {
        "memoryAvailable": "512Mi",
        "nodeFsAvailable": "10%",
        "nodeFsInodesFree": "5%"
      },
      "softEvictionThreshold": {
        "memoryAvailable": "1Gi",
        "nodeFsAvailable": "12%",
        "nodeFsInodesFree": "7%"
      },
      "softEvictionGracePeriod": {
        "memoryAvailable": "30s",
        "nodeFsAvailable": "2m",
        "nodeFsInodesFree": "2m"
      },
      "evictionMaxPodGracePeriodInSeconds": 60
    }
    
  2. Cree un grupo de nodos de Linux que use el archivo de configuración mediante el comando az aks nodepool add con el parámetro --kubelet-config.

    az aks nodepool add \
        --resource-group <resource-group-name> \
        --cluster-name <cluster-name> \
        --name <node-pool-name> \
        --kubelet-config ./nodehardening-kubelet.json
    

    También puede usar el --kubelet-config parámetro con el az aks create comando para aplicar la configuración al grupo de nodos inicial del clúster.

Deshabilitar el endurecimiento de nodos

Deshabilite la protección de nodos mediante el comando az aks update con el parámetro --disable-node-hardening.

Este comando requiere la extensión aks-preview y el indicador de función CustomNodeConfigPreview. Para obtener más información, consulte Requisitos previos.

az aks update \
    --resource-group <resource-group-name> \
    --name <cluster-name> \
    --disable-node-hardening

Deshabilitar la protección de nodos desactiva la configuración de nivel de clúster, pero no se aplica inmediatamente a los nodos existentes. Los nodos existentes mantienen toda la configuración protegida hasta que se reinstale la imagen, por ejemplo, durante una actualización de la imagen del nodo. Después de volver a crear una imagen de nodo, se aplican los siguientes cambios:

  • Se revierte a los valores predeterminados estándar de AKS: Recursos reservados y reservados por el sistema de Kube, umbrales de expulsión duros y cumplimiento de cgroup. La capacidad asignable del nodo aumenta en consecuencia.
  • Conservado: Los umbrales de expulsión no estricta, los períodos de gracia de expulsión no estricta y el período máximo de gracia de terminación del pod durante la expulsión no estricta.

Puede establecer una configuración de kubelet personalizada solo al crear un clúster o grupo de nodos, por lo que no se puede quitar la configuración de expulsión temporal retenida de un grupo de nodos existente. Para quitarlos, cree un nuevo grupo de nodos que anule su configuración explícitamente, mueva las cargas de trabajo al nuevo grupo de nodos y, a continuación, elimine el grupo de nodos antiguo.

  1. Cree un archivo de configuración de kubelet, como remove-soft-eviction.json. En el ejemplo siguiente se establecen todos los umbrales de desalojo flexible y todos los períodos de gracia en una cadena vacía, lo que desactiva el desalojo flexible para esa señal. También establece el período máximo de gracia de terminación del pod en 0, que es el valor predeterminado estándar de AKS.

    {
      "softEvictionThreshold": {
        "memoryAvailable": "",
        "nodeFsAvailable": "",
        "nodeFsInodesFree": ""
      },
      "softEvictionGracePeriod": {
        "memoryAvailable": "",
        "nodeFsAvailable": "",
        "nodeFsInodesFree": ""
      },
      "evictionMaxPodGracePeriodInSeconds": 0
    }
    
  2. Cree un grupo de nodos de Linux que use el archivo de configuración mediante el comando az aks nodepool add con el parámetro --kubelet-config.

    az aks nodepool add \
        --resource-group <resource-group-name> \
        --cluster-name <cluster-name> \
        --name <node-pool-name> \
        --kubelet-config ./remove-soft-eviction.json
    
  3. Mueva las cargas de trabajo al nuevo grupo de nodos y elimine el grupo de nodos anterior. Para obtener más información, consulte Cambiar el tamaño de los grupos de nodos en AKS.

Para confirmar la configuración en un nodo, consulte Comprobación de la configuración de protección de nodos. En los nodos del nuevo grupo de nodos, el valor de evictionSoft está vacío.