En este instructivo, se muestra cómo optimizar el uso de recursos en Google Kubernetes Engine (GKE) configurando cargas de trabajo para que se escale automáticamente a cero réplicas cuando estén inactivas y se vuelvan a escalar a medida que aumente la demanda. Este enfoque integra el escalador automático horizontal de Pods (HPA) con la infraestructura de ajuste de escala automático administrada de GKE para administrar el ajuste de escala en función de métricas externas.
Configura tu implementación para que se escale a cero. Para ello, establece el valor del campo minReplicas en 0 y define una métrica con el tipo External o Object en tu manifiesto de HPA.
GKE supervisa estas métricas a través del recurso personalizado AutoscalingMetric, que ayuda a garantizar una administración eficiente de los recursos para tus aplicaciones.
Con esta configuración, no necesitas usar adaptadores de métricas de terceros, como KEDA, para ajustar la escala de las cargas de trabajo de GKE. Esta solución administra la transferencia de métricas y las recomendaciones de ajuste de escala directamente en el plano de control de GKE, lo que reduce la sobrecarga de administración del clúster.
En este instructivo, implementarás una aplicación de trabajador asíncrono de ejemplo que procesa mensajes de una cola de Pub/Sub. Configuras un escalador automático horizontal de Pods para supervisar la profundidad de la cola (pubsub.googleapis.com:num_undelivered_messages) con un recurso personalizado AutoscalingMetric:
- Cuando llegan mensajes a la suscripción: GKE escala verticalmente los Pods de trabajador para procesar la cola.
- Cuando la cola está vacía: GKE reduce automáticamente la escala de la Deployment de trabajadores a cero réplicas.
Este instructivo está dirigido a desarrolladores de aplicaciones, administradores y operadores de plataformas, y profesionales de DevOps que deseen optimizar el uso de recursos en GKE escalando las cargas de trabajo a cero cuando estén inactivas.
Consideraciones
Antes de configurar las cargas de trabajo para que se escale a cero, revisa las siguientes consideraciones:
- Para escalar cargas de trabajo a cero y desde cero con el HPA, el plano de control y los nodos del clúster de GKE deben ejecutar la versión 1.37 o una posterior en los clústeres nuevos y en los existentes actualizados. Si usas un clúster existente, verifica su versión o actualiza el clúster o sus nodos a la versión 1.37 o posterior.
- Tu manifiesto de HPA debe usar la configuración de
apiVersion: autoscaling/v2para admitir el parámetro de configuración deminReplicas: 0y las métricas externas. - Antes de cambiar a una versión anterior los grupos de nodos a una versión anterior a la 1.37, actualiza todos los manifiestos de HPA configurados para escalar a cero y desde cero estableciendo el campo
minReplicasen1o un valor mayor. Las versiones anteriores a la 1.37 no admiten el parámetro de configuraciónminReplicas: 0, lo que puede hacer que las cargas de trabajo permanezcan atascadas en cero réplicas. - Debes configurar al menos una métrica de
ExternaloObject(como la profundidad de la cola) en tu Horizontal Pod Autoscaler. GKE no puede recopilar métricas de CPU o memoria (Resource) cuando una carga de trabajo tiene cero Pods, por lo que las métricas de recursos por sí solas no pueden activar el ajuste de escala vertical desde cero. - Los objetos AutoscalingMetric, HorizontalPodAutoscaler y Deployment de destino deben residir en el mismo espacio de nombres de Kubernetes.
Antes de comenzar
-
Instala Google Cloud CLI.
-
Configura gcloud CLI para usar tu identidad federada.
Para obtener más información, consulta Accede a la gcloud CLI con tu identidad federada.
-
Para inicializar gcloud CLI, ejecuta el siguiente comando:
gcloud init -
Crea o selecciona un Google Cloud proyecto.
Roles necesarios para seleccionar o crear un proyecto
- Selecciona un proyecto: Para seleccionar un proyecto, no se requiere un rol de IAM específico. Puedes seleccionar cualquier proyecto en el que se te haya otorgado un rol.
-
Crear un proyecto: Para crear un proyecto, necesitas el rol de Creador de proyectos (
roles/resourcemanager.projectCreator), que contiene el permisoresourcemanager.projects.create. Obtén más información para otorgar roles.
-
Crea un proyecto de Google Cloud :
gcloud projects create PROJECT_ID
Reemplaza
PROJECT_IDpor un nombre para el proyecto Google Cloud que estás creando. -
Selecciona el proyecto Google Cloud que creaste:
gcloud config set project PROJECT_ID
Reemplaza
PROJECT_IDpor el nombre de tu proyecto de Google Cloud .
-
Verifica que la facturación esté habilitada para tu proyecto de Google Cloud .
Habilita las APIs de GKE y Pub/Sub:
Roles necesarios para habilitar las APIs
Para habilitar APIs, necesitas el permiso
serviceusage.services.enable. Si creaste el proyecto, es probable que ya tengas este permiso a través del rol de propietario (roles/owner). De lo contrario, puedes obtener este permiso a través del rol de administrador de Service Usage (roles/serviceusage.serviceUsageAdmin). Obtén más información para otorgar roles.gcloud services enable container.googleapis.com
pubsub.googleapis.com
Roles obligatorios
Si quieres obtener los permisos que necesitas para completar este instructivo, pídele a tu administrador que te otorgue los siguientes roles de IAM en tu proyecto:
- Administrador de clústeres de GKE (
roles/container.clusterAdmin) - Administrador de Pub/Sub (
roles/pubsub.admin) - Administrador de IAM de proyecto (
roles/resourcemanager.projectIamAdmin) - Usuario de la cuenta de servicio (
roles/iam.serviceAccountUser)
Para obtener más información sobre cómo otorgar roles, consulta Administra el acceso a proyectos, carpetas y organizaciones.
También puedes obtener los permisos necesarios a través de roles personalizados o cualquier otro rol predefinido.
Configura tu entorno
Para mayor simplicidad, los comandos de este instructivo crean todos los recursos (el clúster de GKE, y el tema y la suscripción de Pub/Sub) dentro de un solo proyecto Google Cloud (PROJECT_ID).
Para configurar tu entorno, sigue estos pasos:
Establece las variables de entorno:
export PROJECT_ID=PROJECT_ID export PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID --format 'get(projectNumber)') export LOCATION=LOCATIONReemplaza lo siguiente:
PROJECT_ID: Es el Google Cloud ID del proyecto.LOCATION: La región o zona en la que deseas crear tu clúster de GKE, comous-central1. Para los clústeres de Autopilot, especifica una región.
Crea un clúster de GKE que ejecute la versión 1.37 o posterior con la Workload Identity Federation for GKE habilitada. Te recomendamos que uses un clúster de Autopilot para una experiencia de Kubernetes completamente administrada y para maximizar el ahorro de costos cuando las cargas de trabajo se reducen a cero. Para elegir el modo de operación que se adapte mejor a tus cargas de trabajo, consulta Elige un modo de operación de GKE:
Autopilot
Crea un clúster de Autopilot:
gcloud container clusters create-auto scale-to-zero \ --project=${PROJECT_ID} \ --location=${LOCATION}Workload Identity Federation for GKE está habilitada de forma predeterminada en los clústeres de Autopilot.
Estándar
Crea un clúster de Standard con la federación de identidades para cargas de trabajo para GKE habilitada:
gcloud container clusters create scale-to-zero \ --project=${PROJECT_ID} \ --location=${LOCATION} \ --workload-pool=${PROJECT_ID}.Configura
kubectlpara comunicarse con tu clúster:gcloud container clusters get-credentials scale-to-zero \ --project=${PROJECT_ID} \ --location=${LOCATION}
Crea recursos de Pub/Sub
En este instructivo, se usa la profundidad de la cola de Pub/Sub como ejemplo de fuente de métricas externas.
Para crear un tema y una suscripción de Pub/Sub, sigue estos pasos:
Crea un tema de Pub/Sub:
gcloud pubsub topics create my-worker-topic \ --project=${PROJECT_ID}Crea una suscripción adjunta al tema:
gcloud pubsub subscriptions create my-worker-subscription \ --topic=my-worker-topic \ --project=${PROJECT_ID}
Configura la federación de identidades para cargas de trabajo para GKE
Configura Workload Identity Federation for GKE para permitir que tu aplicación de trabajador se autentique con las APIs de Google Cloud y consuma mensajes de Pub/Sub.
GKE controla automáticamente la autenticación con Cloud Monitoring para los recursos de AutoscalingMetric en el mismo proyecto. Para obtener más información sobre cómo definir métricas para el ajuste de escala automático, consulta Cómo recuperar métricas externas o personalizadas de Cloud Monitoring.
Para configurar Workload Identity Federation for GKE para tu carga de trabajo de trabajador, sigue estos pasos:
Crea una cuenta de servicio de Kubernetes para tu aplicación de trabajador en el espacio de nombres
default:kubectl create serviceaccount async-worker-sa \ --namespace defaultOtorga el rol
roles/pubsub.subscribera la cuenta de servicio de Kubernetes para que la aplicación pueda recibir mensajes de tu suscripción a Pub/Sub:gcloud projects add-iam-policy-binding projects/${PROJECT_ID} \ --role=roles/pubsub.subscriber \ --member=principal://iam.googleapis.com/projects/${PROJECT_NUMBER}/locations/global/workloadIdentityPools/${PROJECT_ID}./subject/ns/default/sa/async-worker-sa
Si deseas obtener más información, consulta Configura las aplicaciones para usar la federación de identidades para cargas de trabajo para GKE.
Crea la implementación de ejemplo
Antes de poder crear un objeto HPA, debes crear la carga de trabajo que supervisará.
Para crear el Deployment de ejemplo, sigue estos pasos:
Guarda el siguiente manifiesto como
async-worker.yaml:apiVersion: apps/v1 kind: Deployment metadata: name: async-worker namespace: default spec: replicas: 3 selector: matchLabels: app: async-worker template: metadata: labels: app: async-worker spec: containers: - name: async-worker image: nginx:latest ports: - containerPort: 80 resources: limits: memory: 100Mi requests: cpu: 50m memory: 100MiAplica la Deployment de
async-worker.yaml:kubectl apply -f async-worker.yaml
Configura una carga de trabajo para que se escale a cero y desde cero
En esta sección, configurarás la Deployment de async-worker para que se reduzca la escala verticalmente a cero cuando la cola de Pub/Sub esté vacía y vuelva a aumentar a medida que lleguen mensajes nuevos.
Crea el recurso AutoscalingMetric
Para definir el indicador externo que supervisa GKE, crea el recurso personalizado AutoscalingMetric. En el siguiente manifiesto de ejemplo, la métrica consulta Cloud Monitoring para obtener la cantidad de mensajes de Pub/Sub no entregados en la suscripción my-worker-subscription.
Para crear el recurso AutoscalingMetric, sigue estos pasos:
Guarda el siguiente manifiesto como el archivo
pubsub-metric.yaml:apiVersion: autoscaling.gke.io/v1beta1 kind: AutoscalingMetric metadata: name: pubsub-queue-depth namespace: default spec: metrics: - promql: name: pubsub-undelivered query: > { "pubsub.googleapis.com/subscription/num_undelivered_messages", subscription_id="my-worker-subscription" }Aplica el manifiesto
pubsub-metric.yaml:kubectl apply -f pubsub-metric.yamlVerifica el estado de la métrica y recupera su identificador:
kubectl describe autoscalingmetric pubsub-queue-depthEn la sección
Statusdel resultado, verifica que no se muestre ningún error y anota el valor deHpa Nameque se encuentra en el formatoautoscaling.gke.io|CUSTOM_RESOURCE_NAME|METRIC_NAME. Harás referencia a este identificador de métrica externa cuando crees el objeto HorizontalPodAutoscaler en la siguiente sección. Si la secciónStatusinforma errores de configuración o no se recuperan las métricas según lo esperado, consulta Soluciona problemas relacionados con las métricas que se recuperan para el ajuste de escala automático.
Configura el escalador automático horizontal de Pods
Para configurar el comportamiento del ajuste de escala automático, crea un recurso HorizontalPodAutoscaler que apunte al Deployment.
Para configurar el escalador automático horizontal de Pods, sigue estos pasos:
Guarda el siguiente manifiesto como el archivo
worker-hpa.yaml:apiVersion: autoscaling/v2 kind: HorizontalPodAutoscaler metadata: name: async-worker-hpa namespace: default spec: scaleTargetRef: apiVersion: apps/v1 kind: Deployment name: async-worker minReplicas: 0 maxReplicas: 20 metrics: - type: External external: metric: name: autoscaling.gke.io|pubsub-queue-depth|pubsub-undelivered target: type: AverageValue averageValue: "10"Este manifiesto configura los siguientes campos clave:
minReplicas: 0: Habilita la reducción de escala a cero, ya que permite que el controlador reduzca la escala de la Deployment a0réplicas cuando la demanda disminuye a cero.type: External: Configura una fuente de métricas externa para que el HPA pueda activar el aumento de escala cuando la carga de trabajo no tenga Pods.name: autoscaling.gke.io|pubsub-queue-depth|pubsub-undelivered: Asigna el HPA directamente al recurso AutoscalingMetric creado en el paso anterior con el formato del identificadorautoscaling.gke.io|CUSTOM_RESOURCE_NAME|METRIC_NAME.
Aplica el manifiesto
worker-hpa.yaml:kubectl apply -f worker-hpa.yaml
Verifica el comportamiento y las condiciones de la escala cero
Cuando se procesan todos los mensajes de la suscripción a Pub/Sub, el escalador automático horizontal de Pods evalúa la demanda nula y reduce la cantidad de réplicas de la Deployment a 0.
Para verificar que el escalador automático horizontal de Pods activó el estado cero, inspecciona las condiciones de estado del recurso async-worker-hpa ejecutando el siguiente comando:
kubectl describe hpa async-worker-hpa
El resultado es similar a lo siguiente:
Name: async-worker-hpa
Namespace: default
Reference: Deployment/async-worker
Metrics: ( current / target )
"autoscaling.gke.io|pubsub-queue-depth|pubsub-undelivered" (external metric): 0 / 10
Min replicas: 0
Max replicas: 20
Deployment pods: 0 current / 0 desired
Conditions:
Type Status Reason Message
---- ------ ------ -------
AbleToScale True SucceededGetScale the HPA controller was able to get the target's current scale
ScalingActive True ValidMetricFound the HPA was able to successfully calculate a replica count from external metric
ScaledToZero True ScaledToZero the HPA has scaled the target resource to 0 replicas due to zero metric demand
Comprende la condición ScaledToZero
La condición ScaledToZero indica si el escalador automático de Pods horizontal redujo la escala de la carga de trabajo a cero réplicas:
ScaledToZero: True(Reason: ScaledToZero): Indica que el controlador de HPA escaló correctamente tu carga de trabajo a0réplicas porque la demanda de la métrica externa se redujo a cero. El HPA permanece activo (ScalingActive: True) y sondea continuamente GKE para detectar cuándo aumenta la demanda de la carga de trabajo.ScaledToZero: False: Indica que la carga de trabajo se amplió a una o más réplicas.
Si ajustas la escala de una Deployment a cero réplicas de forma manual, por ejemplo, con el comando kubectl scale --replicas=0, el HPA pausa el ajuste de escala automático (ScalingActive:
False) para evitar cambios en conflicto. Para reanudar el ajuste de escala automático, vuelve a ajustar la escala de la implementación a una o más réplicas (kubectl scale deployment
async-worker --replicas=1).
Para solucionar problemas en situaciones en las que las cargas de trabajo no se pueden escalar a cero o no se pueden escalar verticalmente desde cero, consulta Soluciona problemas de escalamiento de cargas de trabajo de GKE a cero y desde cero con HPA. Si el escalador automático de Pods horizontal informa que faltan métricas externas o que no son válidas, consulta Soluciona problemas relacionados con las métricas que se recuperan para el ajuste de escala automático.
Realiza una limpieza
Sigue estos pasos para evitar que se apliquen cargos a tu cuenta de Google Cloud por los recursos que usaste en este instructivo:
Borra el clúster de GKE:
gcloud container clusters delete scale-to-zero \ --project=${PROJECT_ID} \ --location=${LOCATION}Borra el tema y la suscripción de Pub/Sub:
gcloud pubsub subscriptions delete my-worker-subscription \ --project=${PROJECT_ID} gcloud pubsub topics delete my-worker-topic \ --project=${PROJECT_ID}
¿Qué sigue?
- Aprende a mitigar la latencia de inicio en frío con los búferes de capacidad de GKE.
- Obtén información para diagnosticar problemas de escalamiento cuando se escala a cero y desde cero con HPA.