Poner los nodos en modo de mantenimiento

Cuando necesites reparar o mantener nodos, primero debes ponerlos en modo de mantenimiento. Esto agota los pods y las cargas de trabajo actuales de forma gradual, excepto los pods del sistema críticos, como el servidor de la API. El modo de mantenimiento también impide que el nodo reciba nuevas asignaciones de pods. En el modo de mantenimiento, puedes trabajar en tus nodos sin riesgo de interrumpir el tráfico de pods.

Cómo funciona

Google Distributed Cloud ofrece una forma de poner los nodos en modo de mantenimiento. Este enfoque permite que otros componentes del clúster sepan correctamente que el nodo está en modo de mantenimiento. Cuando pones un nodo en modo de mantenimiento, no se pueden programar pods adicionales en el nodo y los pods que ya hay se detienen.

En lugar de usar el modo de mantenimiento, puedes usar manualmente comandos de Kubernetes, como kubectl cordon y kubectl drain, en un nodo específico.

Cuando usas el proceso del modo de mantenimiento, Google Distributed Cloud hace lo siguiente:

1,29

  • Google Distributed Cloud añade el baremetal.cluster.gke.io/maintenance:NoSchedule taint a los nodos especificados para evitar que se programen nuevos pods en el nodo.

  • Google Distributed Cloud usa la API de desalojo para desalojar cada pod. Este método de drenaje de nodos respeta los presupuestos de interrupción de pods (PDBs). Puedes configurar PDBs para proteger tus cargas de trabajo especificando un nivel tolerable de interrupción para un conjunto de pods mediante los campos minAvailable y maxUnavailable. De esta forma, los nodos se protegen mejor frente a las interrupciones de las cargas de trabajo. El drenaje de nodos basado en desalojo está disponible como versión GA para la versión 1.29.

  • Se aplica un tiempo de espera de 20 minutos para asegurarse de que los nodos no se queden esperando a que se detengan los pods. Es posible que los pods no se detengan si están configurados para tolerar todos los taints o si tienen finalizadores. Google Distributed Cloud intenta detener todos los pods, pero si se supera el tiempo de espera, el nodo se pone en modo de mantenimiento. Este tiempo de espera evita que los pods en ejecución bloqueen las actualizaciones.

1.28 y versiones anteriores

  • Google Distributed Cloud añade el baremetal.cluster.gke.io/maintenance:NoSchedule taint a los nodos especificados para evitar que se programen nuevos pods en el nodo.

  • Google Distributed Cloud añade el taint baremetal.cluster.gke.io/maintenance:NoExecute. En función del taint NoExecute, Google Distributed Cloud kube-scheduler detiene los pods y vacía el nodo. Este método de drenaje de nodos no respeta los PDBs.

  • Se aplica un tiempo de espera de 20 minutos para asegurarse de que los nodos no se queden esperando a que se detengan los pods. Es posible que los pods no se detengan si están configurados para tolerar todos los taints o si tienen finalizadores. Google Distributed Cloud intenta detener todos los pods, pero si se supera el tiempo de espera, el nodo se pone en modo de mantenimiento. Este tiempo de espera evita que los pods en ejecución bloqueen las actualizaciones.

Drenaje basado en desahucios

No hay cambios en los procedimientos asociados al cambio de drenaje de nodos basado en desalojo al drenaje basado en taints. El cambio solo afecta a la lógica de conciliación.

Esta función no está en la misma fase de lanzamiento en todas las versiones compatibles:

  • 1.29: GA
  • 1.28: no disponible
  • 1.16: no disponible

Orden de drenaje

Antes de la versión 1.29, el drenaje de nodos basado en taints que realiza Google Distributed Cloud kube-scheduler no empleaba ningún algoritmo concreto para drenar pods de un nodo. Con el drenaje de nodos basado en la expulsión, los pods se expulsan en un orden específico en función de la prioridad. La prioridad de desalojo se asocia a criterios de pods específicos, tal como se muestra en la siguiente tabla:

Orden de drenaje Criterios de los pods (deben coincidir con todos) y
1

Se expulsan los pods que cumplen los siguientes criterios:

  • Pods sin spec.prorityClassName
  • Pods que no coinciden con ningún nombre de interfaz de almacenamiento de contenedores (CSI) conocido
  • Pods que no pertenecen a un DaemonSet
2

Se expulsan los pods que cumplen los siguientes criterios:

  • Pods que pertenecen a un DaemonSet
  • Los pods no tienen PriorityClass
  • Pods que no coinciden con ningún nombre de interfaz de almacenamiento de contenedores (CSI) conocido
3

Se expulsan los pods que cumplen los siguientes criterios:

  • Pods con Spec.ProrityClassName
  • Pods que no coinciden con ningún nombre de interfaz de almacenamiento de contenedores (CSI) conocido

El orden de desalojo de los pods coincidentes se basa en PriorityClass.value, de menor a mayor.

4

Espera a que CSI limpie los montajes de PV/PVC después de que se hayan expulsado todos los pods. Usa Node.Status.VolumesInUse para indicar que se han limpiado todos los volúmenes.

5

Se expulsan los pods que cumplen los siguientes criterios:

  • Pods que coinciden con un nombre de interfaz de almacenamiento de contenedor (CSI) conocido

Estos pods aún necesitan purgarse, ya que kubelet no proporciona compatibilidad con la actualización in situ.

Como el drenaje de nodos basado en desalojo respeta los PDBs, los ajustes de los PDBs pueden bloquear el drenaje de nodos en algunas circunstancias. Para obtener información sobre cómo solucionar problemas relacionados con el vaciado de grupos de nodos, consulta Comprobar por qué un nodo ha estado en estado de vaciado durante mucho tiempo.

Inhabilitar el drenaje de nodos basado en desalojos

El drenaje de nodos basado en desalojos está habilitado de forma predeterminada en los clústeres con la versión secundaria 1.29 o posterior, o en los clústeres que se actualicen a la versión secundaria 1.29 o posterior. Si el drenaje de nodos basado en desalojo está causando problemas con las actualizaciones o el mantenimiento del clúster, puedes volver al drenaje de nodos basado en taints añadiendo la anotación baremetal.cluster.gke.io/maintenance-mode-ignore-pdb: "" al recurso de clúster.

Para restaurar el comportamiento predeterminado de drenaje de nodos basado en la expulsión, elimina por completo la anotación. Si se define la anotación como false, no se vuelve a habilitar el comportamiento predeterminado.

Poner un nodo en modo de mantenimiento

Elige los nodos que quieras poner en modo de mantenimiento especificando los intervalos de IP de los nodos seleccionados en maintenanceBlocks del archivo de configuración del clúster. Los nodos que elijas deben estar en estado preparado y funcionar en el clúster.

Para poner los nodos en modo de mantenimiento, sigue estos pasos:

  1. Edita el archivo de configuración del clúster para seleccionar los nodos que quieras poner en modo de mantenimiento.

    Puedes editar el archivo de configuración con el editor que quieras o editar el recurso personalizado del clúster directamente ejecutando el siguiente comando:

    kubectl -n CLUSTER_NAMESPACE edit cluster CLUSTER_NAME

    Haz los cambios siguientes:

    • CLUSTER_NAMESPACE: el espacio de nombres del clúster.
    • CLUSTER_NAME: el nombre del clúster.
  2. Añade la sección maintenanceBlocks al archivo de configuración del clúster para especificar una sola dirección IP o un intervalo de direcciones para los nodos que quieras poner en modo de mantenimiento.

    En el siguiente ejemplo se muestra cómo seleccionar varios nodos especificando un intervalo de direcciones IP:

    metadata:
      name: my-cluster
      namespace: cluster-my-cluster
    spec:
      maintenanceBlocks:
        cidrBlocks:
        - 172.16.128.1-172.16.128.64
    
  3. Guarda y aplica la configuración actualizada del clúster.

    Google Distributed Cloud empieza a poner los nodos en modo de mantenimiento.

  4. Ejecuta el siguiente comando para obtener el estado de los nodos de tu clúster:

    kubectl get nodes --kubeconfig=KUBECONFIG

    El resultado debería ser similar al siguiente:

    NAME                STATUS   ROLES           AGE     VERSION
    user-baremetal-01   Ready    control-plane   2d22h   v1.27.4-gke.1600
    user-baremetal-04   Ready    worker          2d22h   v1.27.4-gke.1600
    user-baremetal-05   Ready    worker          2d22h   v1.27.4-gke.1600
    user-baremetal-06   Ready    worker          2d22h   v1.27.4-gke.1600
    

    Ten en cuenta que los nodos se pueden seguir programando, pero los taints impiden que se programen pods (sin una tolerancia adecuada) en el nodo.

  5. Ejecuta el siguiente comando para obtener el número de nodos en modo de mantenimiento:

    kubectl get nodepools --kubeconfig ADMIN_KUBECONFIG 
    

    La respuesta debería ser similar al siguiente ejemplo:

    NAME   READY   RECONCILING   STALLED   UNDERMAINTENANCE   UNKNOWN
    np1    3       0             0         1                  0
    

    La columna UNDERMAINTENANCE de este ejemplo muestra que un nodo está en modo de mantenimiento.

    Google Distributed Cloud también añade los siguientes taints a los nodos cuando se ponen en modo de mantenimiento:

    • baremetal.cluster.gke.io/maintenance:NoExecute
    • baremetal.cluster.gke.io/maintenance:NoSchedule

Quitar un nodo del modo de mantenimiento

Para quitar nodos del modo de mantenimiento, sigue estos pasos:

  1. Edita el archivo de configuración del clúster para borrar los nodos que quieras quitar del modo de mantenimiento.

    Puedes editar el archivo de configuración con el editor que quieras o editar el recurso personalizado del clúster directamente ejecutando el siguiente comando:

    kubectl -n CLUSTER_NAMESPACE edit cluster CLUSTER_NAME

    Haz los cambios siguientes:

    • CLUSTER_NAMESPACE: el espacio de nombres del clúster.
    • CLUSTER_NAME: el nombre del clúster.
  2. Edita las direcciones IP para quitar nodos específicos del modo de mantenimiento o elimina la sección maintenanceBlocks para quitar todos los nodos del modo de mantenimiento.

  3. Guarda y aplica la configuración actualizada del clúster.

  4. Usa los comandos de kubectl para comprobar el estado de tus nodos.

Apagar y reiniciar un clúster

Si es necesario desactivar un clúster completo, sigue las instrucciones de las secciones siguientes para apagarlo y volver a activarlo de forma segura.

Apagar un clúster

Si vas a apagar un clúster que gestiona clústeres de usuarios, primero debes apagar todos los clústeres de usuarios gestionados. Las siguientes instrucciones se aplican a todos los tipos de clúster de Google Distributed Cloud.

  1. Comprueba el estado de todos los nodos del clúster:

    kubectl get nodes --kubeconfig CLUSTER_KUBECONFIG
    

    Sustituye CLUSTER_KUBECONFIG por la ruta del archivo kubeconfig del clúster.

    El resultado debería ser similar al siguiente:

    NAME        STATUS   ROLES           AGE    VERSION
    control-0   Ready    control-plane   202d   v1.27.4-gke.1600
    control-1   Ready    control-plane   202d   v1.27.4-gke.1600
    control-2   Ready    control-plane   202d   v1.27.4-gke.1600
    worker-0    Ready    worker          202d   v1.27.4-gke.1600
    worker-1    Ready    worker          202d   v1.27.4-gke.1600
    worker-2    Ready    worker          202d   v1.27.4-gke.1600
    worker-3    Ready    worker          202d   v1.27.4-gke.1600
    worker-4    Ready    worker          154d   v1.27.4-gke.1600
    worker-5    Ready    worker          154d   v1.27.4-gke.1600
    worker-6    Ready    worker          154d   v1.27.4-gke.1600
    worker-7    Ready    worker          154d   v1.27.4-gke.1600
    worker-8    Ready    worker          154d   v1.27.4-gke.1600
    worker-9    Ready    worker          154d   v1.27.4-gke.1600
    

    Si el STATUS de un nodo no es Ready, te recomendamos que soluciones los problemas del nodo y que solo continúes cuando todos los nodos sean Ready.

  2. Si vas a apagar un clúster de usuario, comprueba el estado de los nodos del clúster de administrador:

    kubectl get nodes --kubeconfig ADMIN_KUBECONFIG
    

    Sustituye ADMIN_KUBECONFIG por la ruta del archivo kubeconfig del clúster de gestión.

    Los pasos posteriores dependen del clúster de administrador. Si el STATUS de un nodo no es Ready, te recomendamos encarecidamente que resuelvas los problemas del nodo y que solo continúes cuando todos los nodos sean Ready.

  3. Comprueba el estado del clúster que quieras apagar:

    bmctl check cluster -c CLUSTER_NAME --kubeconfig ADMIN_KUBECONFIG
    

    Haz los cambios siguientes:

    • CLUSTER_NAME: el nombre del clúster que quieres comprobar.

    • ADMIN_KUBECONFIG: la ruta del archivo kubeconfig del clúster de gestión.

    Corrige los problemas que se hayan detectado antes de continuar.

  4. En el clúster que vas a cerrar, asegúrate de que todos los etcd pods estén en ejecución:

    kubectl get pods --kubeconfig CLUSTER_KUBECONFIG -A \
        -l component=etcd
    

    Sustituye CLUSTER_KUBECONFIG por la ruta del archivo kubeconfig del clúster.

    El resultado debería ser similar al siguiente:

    NAMESPACE     NAME                   READY   STATUS    RESTARTS   AGE
    kube-system   etcd-control-0-admin   1/1     Running   0          2d22h
    kube-system   etcd-control-1-admin   1/1     Running   0          2d22h
    kube-system   etcd-control-2-admin   1/1     Running   0          2d22h
    

    Si el STATUS de un pod no es Running, te recomendamos que soluciones el problema del pod y que continúes solo cuando todos los pods sean Running.

  5. Crea una copia de seguridad tal como se describe en Crear una copia de seguridad de un clúster.

    Es importante crear una copia de seguridad de etcd antes de apagar el clúster para que se pueda restaurar si tienes algún problema al reiniciarlo. La corrupción de etcd, los fallos de hardware de los nodos, los problemas de conectividad de red y otras condiciones pueden impedir que el clúster se reinicie correctamente.

  6. Si vas a apagar un clúster con nodos de trabajo, pon los nodos de trabajo en modo de mantenimiento.

    Este paso minimiza la cantidad de escritura en etcd, lo que reduce la probabilidad de que se tenga que conciliar una gran cantidad de escrituras de etcd cuando se reinicie el clúster.

  7. Pon los nodos del plano de control en modo de mantenimiento.

    Este paso evita que se produzcan escrituras dañadas en cargas de trabajo con estado durante el apagado de los nodos.

  8. Apaga los nodos del clúster en el siguiente orden:

    1. Nodos de trabajador
    2. Nodos del balanceador de carga del plano de control
    3. Nodos del plano de control, empezando por los seguidores de etcd y terminando por el líder de etcd

      Si tienes un clúster de alta disponibilidad, puedes encontrar el líder de etcd conectándote a cada nodo del plano de control mediante SSH y ejecutando el siguiente comando etcdctl:

      ETCDCTL_API=3 etcdctl \
          --cacert /etc/kubernetes/pki/etcd/ca.crt \
          --cert /etc/kubernetes/pki/etcd/server.crt \
          --key /etc/kubernetes/pki/etcd/server.key \
          --write-out=table endpoint status
      

      La respuesta incluye una columna IS LEADER, que devuelve true si el nodo es el líder de etcd.

En este punto, el clúster se habrá apagado por completo. Una vez que hayas realizado el mantenimiento necesario, puedes reiniciar el clúster como se describe en la siguiente sección.

Reiniciar el clúster

Sigue estos pasos para reiniciar un clúster que se haya apagado por completo.

  1. Enciende las máquinas de los nodos en el orden inverso al de la secuencia de apagado.

  2. Quita los nodos del plano de control del modo de mantenimiento.

    Para obtener instrucciones, consulta Quitar un nodo del modo de mantenimiento.

  3. Quita los nodos de trabajo del modo de mantenimiento.

  4. Ejecuta comprobaciones del estado del clúster para asegurarte de que funciona correctamente:

    bmctl check cluster -c CLUSTER_NAME --kubeconfig ADMIN_KUBECONFIG
    
  5. Si un problema, como un bucle de fallos de etcd, impide que el clúster se reinicie correctamente, prueba a restaurarlo a partir de la última copia de seguridad correcta conocida. Para obtener instrucciones, consulta Restaurar un clúster.

Modo de facturación y mantenimiento

La facturación de Google Distributed Cloud se basa en el número de vCPUs que tiene tu clúster para los nodos capaces de ejecutar cargas de trabajo. Cuando pones un nodo en modo de mantenimiento, se añaden los taints NoExecute y NoSchedule al nodo, pero no se inhabilita la facturación. Después de poner un nodo en modo de mantenimiento, acordonar el nodo (kubectl cordon NODE_NAME) para marcarlo como no programable. Una vez que un nodo se marca como no programable, el nodo y sus vCPUs asociados se excluyen de la facturación.

Como se describe en la página de precios, puedes usar kubectl para ver la capacidad de vCPU (que se usa para la facturación) de cada uno de tus clústeres de usuario. El comando no tiene en cuenta si el nodo se puede programar o no, sino que solo proporciona el número de vCPUs por nodo.

Para identificar el número de vCPUs por nodo de tu clúster de usuario, haz lo siguiente:

kubectl get nodes \
    --kubeconfig USER_KUBECONFIG \
    -o=jsonpath="{range .items[*]}{.metadata.name}{\"\t\"} \
    {.status.capacity.cpu}{\"\n\"}{end}"

Sustituye USER_KUBECONFIG por la ruta del archivo kubeconfig de tu clúster de usuario.