Configura la puerta de enlace de inferencia de varios clústeres de GKE

En este documento, se describe cómo configurar la puerta de enlace de inferencia de varios clústeres de Google Kubernetes Engine (GKE) para balancear la carga de forma inteligente de tus cargas de trabajo de inferencia de IA/ML en varios clústeres de GKE, que pueden abarcar diferentes regiones. Esta configuración usa la API de Gateway, Ingress de varios clústeres y recursos personalizados, como InferencePool y InferenceObjective, para mejorar la escalabilidad, ayudar a garantizar la alta disponibilidad y optimizar el uso de recursos para tus implementaciones de servicio de modelos.

Para comprender este documento, debes conocer lo siguiente:

Este documento está dirigido a las siguientes personas:

  • Ingenieros de aprendizaje automático (AA), administradores y operadores de plataformas, o especialistas en IA y datos que deseen usar las capacidades de organización de contenedores de GKE para entregar cargas de trabajo de IA/AA
  • Arquitectos de nube o especialistas en redes que interactúan con las redes de GKE

Para obtener más información sobre los roles comunes y las tareas de ejemplo a las que se hace referencia en el contenido deGoogle Cloud , consulta Roles de usuario y tareas comunes de GKE Enterprise.

Antes de comenzar

Antes de comenzar, asegúrate de haber realizado las siguientes tareas:

  • Habilita la API de Google Kubernetes Engine.
  • Habilitar la API de Google Kubernetes Engine
  • Si deseas usar Google Cloud CLI para esta tarea, instala y, luego, inicializa gcloud CLI. Si ya instalaste gcloud CLI, ejecuta el comando gcloud components update para obtener la versión más reciente. Es posible que las versiones anteriores de gcloud CLI no admitan la ejecución de los comandos que se describen en este documento.
  • Habilita las API de Compute Engine, Google Kubernetes Engine, Model Armor y Network Services.

    Ve a Habilita el acceso a las APIs y sigue las instrucciones.

  • Habilita la API de Autoscaling.

    Ve a la API de ajuste de escala automático y sigue las instrucciones.

  • Requisitos previos de Hugging Face:

    • Crea una cuenta de Hugging Face si aún no tienes una.
    • Solicita y obtén la aprobación para acceder al modelo de Llama 3.1 en Hugging Face.
    • Firma el acuerdo de consentimiento de licencia en la página del modelo en Hugging Face.
    • Genera un token de acceso de Hugging Face con, al menos, permisos de Read.

Requisitos

  • Asegúrate de que tu proyecto tenga la cuota suficiente para las GPU H100. Para obtener más información, consulta Planifica la cuota de GPU y Cuotas de asignación.
  • Usa la versión 1.34.1-gke.1127000 de GKE o una posterior.
  • Usa la versión 480.0.0 o posterior de gcloud CLI.
  • Tus cuentas de servicio de nodos deben tener permisos para escribir métricas en la API de Autoscaling.
  • Debes tener los siguientes roles de IAM en el proyecto: roles/container.admin y roles/iam.serviceAccountAdmin.

Configura la puerta de enlace de inferencia de varios clústeres

Para configurar la puerta de enlace de inferencia de varios clústeres de GKE, sigue estos pasos:

Crea clústeres y grupos de nodos

Para alojar tus cargas de trabajo de inferencia de IA/AA y habilitar el balanceo de cargas entre regiones, crea dos clústeres de GKE en regiones diferentes, cada uno con un grupo de nodos de GPU H100.

  1. Crea el primer clúster:

    gcloud container clusters create CLUSTER_1_NAME \
        --region LOCATION \
        --project=PROJECT_ID \
        --gateway-api=standard \
        --release-channel "rapid" \
        --cluster-version=GKE_VERSION \
        --machine-type="MACHINE_TYPE" \
        --disk-type="DISK_TYPE" \
        --enable-managed-prometheus --monitoring=SYSTEM,DCGM \
        --hpa-profile=performance \
        --async # Allows the command to return immediately
    

    Reemplaza lo siguiente:

    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.
    • LOCATION: la región del primer clúster, por ejemplo, europe-west3.
    • PROJECT_ID: el ID de tu proyecto
    • GKE_VERSION: Es la versión de GKE que se usará, por ejemplo, 1.34.1-gke.1127000.
    • MACHINE_TYPE: Es el tipo de máquina para los nodos del clúster, por ejemplo, c2-standard-16.
    • DISK_TYPE: Es el tipo de disco para los nodos del clúster, por ejemplo, pd-standard.
  2. Crea un grupo de nodos H100 para el primer clúster:

    gcloud container node-pools create NODE_POOL_NAME \
        --accelerator "type=nvidia-h100-80gb,count=2,gpu-driver-version=latest" \
        --project=PROJECT_ID \
        --location=CLUSTER_1_ZONE \
        --node-locations=CLUSTER_1_ZONE \
        --cluster=CLUSTER_1_NAME \
        --machine-type=NODE_POOL_MACHINE_TYPE \
        --num-nodes=NUM_NODES \
        --spot \
        --async # Allows the command to return immediately
    

    Reemplaza lo siguiente:

    • NODE_POOL_NAME: el nombre del grupo de nodos, por ejemplo, h100
    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_1_ZONE: Es la zona del primer clúster, por ejemplo, europe-west3-c.
    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.
    • NODE_POOL_MACHINE_TYPE: Es el tipo de máquina del grupo de nodos, por ejemplo, a3-highgpu-2g.
    • NUM_NODES: Es la cantidad de nodos en el grupo de nodos, por ejemplo, 3.
  3. Obtén las credenciales:

    gcloud container clusters get-credentials CLUSTER_1_NAME \
        --location CLUSTER_1_ZONE \
        --project=PROJECT_ID
    

    Reemplaza lo siguiente:

    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.
    • CLUSTER_1_ZONE: Es la zona del primer clúster, por ejemplo, europe-west3-c.
  4. En el primer clúster, crea un secreto para el token de Hugging Face:

    kubectl create secret generic hf-token \
        --from-literal=token=HF_TOKEN
    

    Reemplaza HF_TOKEN por tu token de acceso de Hugging Face.

  5. Crea el segundo clúster en una región diferente a la del primer clúster:

    gcloud container clusters create gke-east --region LOCATION \
        --project=PROJECT_ID \
        --gateway-api=standard \
        --release-channel "rapid" \
        --cluster-version=GKE_VERSION \
        --machine-type="MACHINE_TYPE" \
        --disk-type="DISK_TYPE" \
        --enable-managed-prometheus \
        --monitoring=SYSTEM,DCGM \
        --hpa-profile=performance \
        --async # Allows the command to return immediately while the
    cluster is created in the background.
    

    Reemplaza lo siguiente:

    • LOCATION: Es la región del segundo clúster. Debe ser una región diferente a la del primer clúster. Por ejemplo, us-east4
    • PROJECT_ID: el ID de tu proyecto
    • GKE_VERSION: Es la versión de GKE que se usará, por ejemplo, 1.34.1-gke.1127000.
    • MACHINE_TYPE: Es el tipo de máquina para los nodos del clúster, por ejemplo, c2-standard-16.
    • DISK_TYPE: Es el tipo de disco para los nodos del clúster, por ejemplo, pd-standard.
  6. Crea un grupo de nodos H100 para el segundo clúster:

    gcloud container node-pools create h100 \
        --accelerator "type=nvidia-h100-80gb,count=2,gpu-driver-version=latest" \
        --project=PROJECT_ID \
        --location=CLUSTER_2_ZONE \
        --node-locations=CLUSTER_2_ZONE \
        --cluster=CLUSTER_2_NAME \
        --machine-type=NODE_POOL_MACHINE_TYPE \
        --num-nodes=NUM_NODES \
        --spot \
        --async # Allows the command to return immediately
    

    Reemplaza lo siguiente:

    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_2_ZONE: Es la zona del segundo clúster, por ejemplo, us-east4-a.
    • CLUSTER_2_NAME: Es el nombre del segundo clúster, por ejemplo, gke-east.
    • NODE_POOL_MACHINE_TYPE: Es el tipo de máquina del grupo de nodos, por ejemplo, a3-highgpu-2g.
    • NUM_NODES: Es la cantidad de nodos en el grupo de nodos, por ejemplo, 3.
  7. Para el segundo clúster, obtén credenciales y crea un secreto para el token de Hugging Face:

    gcloud container clusters get-credentials CLUSTER_2_NAME \
        --location CLUSTER_2_ZONE \
        --project=PROJECT_ID
    
    kubectl create secret generic hf-token --from-literal=token=HF_TOKEN
    

    Reemplaza lo siguiente:

    • CLUSTER_2_NAME: Es el nombre del segundo clúster, por ejemplo, gke-east.
    • CLUSTER_2_ZONE: Es la zona del segundo clúster, por ejemplo, us-east4-a.
    • PROJECT_ID: el ID de tu proyecto
    • HF_TOKEN: Tu token de acceso de Hugging Face.

Registra clústeres en una flota

Para habilitar las capacidades de varios clústeres, como la puerta de enlace de inferencia de varios clústeres de GKE, registra tus clústeres en una flota.

  1. Registra ambos clústeres en la flota de tu proyecto:

    gcloud container fleet memberships register CLUSTER_1_NAME \
        --gke-cluster CLUSTER_1_ZONE/CLUSTER_1_NAME \
        --location=global \
        --project=PROJECT_ID
    
    gcloud container fleet memberships register CLUSTER_2_NAME \
        --gke-cluster CLUSTER_2_ZONE/CLUSTER_2_NAME \
        --location=global \
        --project=PROJECT_ID
    

    Reemplaza lo siguiente:

    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.
    • CLUSTER_1_ZONE: Es la zona del primer clúster, por ejemplo, europe-west3-c.
    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_2_NAME: Es el nombre del segundo clúster, por ejemplo, gke-east.
    • CLUSTER_2_ZONE: Es la zona del segundo clúster, por ejemplo, us-east4-a.
  2. Para permitir que una sola puerta de enlace administre el tráfico en varios clústeres, habilita la función de Ingress de varios clústeres y designa un clúster de configuración:

    gcloud container fleet ingress enable \
        --config-membership=projects/PROJECT_ID/locations/global/memberships/CLUSTER_1_NAME
    

    Reemplaza lo siguiente:

    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.

Crea subredes de solo proxy

En el caso de una puerta de enlace interna, crea una subred de solo proxy en cada región. Los proxies de Envoy de la puerta de enlace interna usan estas subredes dedicadas para controlar el tráfico dentro de tu red de VPC.

  1. Crea una subred en la región del primer clúster:

    gcloud compute networks subnets create CLUSTER_1_REGION-subnet \
        --purpose=GLOBAL_MANAGED_PROXY \
        --role=ACTIVE \
        --region=CLUSTER_1_REGION \
        --network=default \
        --range=10.0.0.0/23 \
        --project=PROJECT_ID
    
  2. Crea una subred en la región del segundo clúster:

    gcloud compute networks subnets create CLUSTER_2_REGION-subnet \
        --purpose=GLOBAL_MANAGED_PROXY \
        --role=ACTIVE \
        --region=CLUSTER_2_REGION \
        --network=default \
        --range=10.5.0.0/23 \
        --project=PROJECT_ID
    

    Reemplaza lo siguiente:

    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_1_REGION: Es la región del primer clúster, por ejemplo, europe-west3.
    • CLUSTER_2_REGION: Es la región del segundo clúster, por ejemplo, us-east4.

Instala las CRD requeridas

La puerta de enlace de inferencia de varios clústeres de GKE usa recursos personalizados, como InferencePool y InferenceObjective. El controlador de la API de GKE Gateway administra la definición de recurso personalizado (CRD) InferencePool. Sin embargo, debes instalar manualmente la CRD InferenceObjective, que se encuentra en versión alfa, en tus clústeres.

  1. Define variables de contexto para tus clústeres:

    CLUSTER1_CONTEXT="gke_PROJECT_ID_CLUSTER_1_ZONE_CLUSTER_1_NAME"
    CLUSTER2_CONTEXT="gke_PROJECT_ID_CLUSTER_2_ZONE_CLUSTER_2_NAME"
    

    Reemplaza lo siguiente:

    • PROJECT_ID: el ID de tu proyecto
    • CLUSTER_1_ZONE: Es la zona del primer clúster, por ejemplo, europe-west3-c.
    • CLUSTER_1_NAME: Es el nombre del primer clúster, por ejemplo, gke-west.
    • CLUSTER_2_ZONE: Es la zona del segundo clúster, por ejemplo, us-east4-a.
    • CLUSTER_2_NAME: Es el nombre del segundo clúster, por ejemplo, gke-east.
  2. Instala el CRD InferenceObjective en ambos clústeres:

    # Copyright 2025 Google LLC
    #
    # Licensed under the Apache License, Version 2.0 (the "License");
    # you may not use this file except in compliance with the License.
    # You may obtain a copy of the License at
    #
    #      http://www.apache.org/licenses/LICENSE-2.0
    #
    # Unless required by applicable law or agreed to in writing, software
    # distributed under the License is distributed on an "AS IS" BASIS,
    # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    # See the License for the specific language governing permissions and
    # limitations under the License.
    
    apiVersion: admissionregistration.k8s.io/v1
    kind: ValidatingAdmissionPolicy
    metadata:
      name: restrict-toleration
    spec:
      failurePolicy: Fail
      paramKind:
        apiVersion: v1
        kind: ConfigMap
      matchConstraints:
        # GKE will mutate any pod specifying a CC label in a nodeSelector
        # or in a nodeAffinity with a toleration for the CC node label.
        # Mutation hooks will always mutate the K8s object before validating
        # the admission request.  
        # Pods created by Jobs, CronJobs, Deployments, etc. will also be validated.
        # See https://kubernetes.io/docs/reference/access-authn-authz/admission-controllers/#admission-control-phases for details
        resourceRules:
        - apiGroups:   [""]
          apiVersions: ["v1"]
          operations:  ["CREATE", "UPDATE"]
          resources:   ["pods"]
      matchConditions:
        - name: 'match-tolerations'
          # Validate only if compute class toleration exists
          # and the CC label tolerated is listed in the configmap.
          expression: > 
            object.spec.tolerations.exists(t, has(t.key) &&
            t.key == 'cloud.google.com/compute-class' &&
            params.data.computeClasses.split('\\n').exists(cc, cc == t.value))
      validations:
        # ConfigMap with permitted namespace list referenced via `params`.
        - expression: "params.data.namespaces.split('\\n').exists(ns, ns == object.metadata.namespace)"
          messageExpression: "'Compute class toleration not permitted on workloads in namespace ' + object.metadata.namespace"
    
    ---
    apiVersion: admissionregistration.k8s.io/v1
    kind: ValidatingAdmissionPolicyBinding
    metadata:
      name: restrict-toleration-binding
    spec:
      policyName: restrict-toleration
      validationActions: ["Deny"]
      paramRef:
        name: allowed-ccc-namespaces
        namespace: default
        parameterNotFoundAction: Deny
    ---
    apiVersion: v1
    kind: ConfigMap
    metadata:
      name: allowed-ccc-namespaces
      namespace: default
    data:
      # Replace example namespaces in line-separated list below.
      namespaces: |
        foo
        bar
        baz
      # ComputeClass names to monitor with this validation policy.
      # The 'autopilot' and 'autopilot-spot' CCs are present on
      # all NAP Standard and Autopilot clusters.
      computeClasses: |
        MY_COMPUTE_CLASS
        autopilot
        autopilot-spot
    
    
    kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/gateway-api-inference-extension/v1.1.0/config/crd/bases/inference.networking.x-k8s.io_inferenceobjectives.yaml --context=CLUSTER1_CONTEXT
    
    kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/gateway-api-inference-extension/v1.1.0/config/crd/bases/inference.networking.x-k8s.io_inferenceobjectives.yaml --context=CLUSTER2_CONTEXT
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.

Implementa recursos en los clústeres de destino

Para que tus cargas de trabajo de inferencia de IA/AA estén disponibles en cada clúster, implementa los recursos necesarios, como los servidores de modelos y los recursos personalizados de InferenceObjective.

  1. Implementa los servidores de modelos en ambos clústeres:

    kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/gateway-api-inference-extension/v1.1.0/config/manifests/vllm/gpu-deployment.yaml --context=CLUSTER1_CONTEXT
    
    kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/gateway-api-inference-extension/v1.1.0/config/manifests/vllm/gpu-deployment.yaml --context=CLUSTER2_CONTEXT
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.
  2. Implementa los recursos InferenceObjective en ambos clústeres. Guarda el siguiente manifiesto de muestra en un archivo llamado inference-objective.yaml:

    apiVersion: inference.networking.x-k8s.io/v1alpha2
    kind: InferenceObjective
    metadata:
      name: food-review
    spec:
      priority: 10
      poolRef:
        name: llama3-8b-instruct
        group: "inference.networking.k8s.io"
    
  3. Aplica el manifiesto a ambos clústeres:

    kubectl apply -f inference-objective.yaml --context=CLUSTER1_CONTEXT
    kubectl apply -f inference-objective.yaml --context=CLUSTER2_CONTEXT
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.
  4. Implementa los recursos InferencePool en ambos clústeres con Helm:

    helm install vllm-llama3-8b-instruct \
      --kube-context CLUSTER1_CONTEXT \
      --set inferencePool.modelServers.matchLabels.app=vllm-llama3-8b-instruct \
      --set provider.name=gke \
      --version v1.1.0 \
      oci://registry.k8s.io/gateway-api-inference-extension/charts/inferencepool
    
    helm install vllm-llama3-8b-instruct \
      --kube-context CLUSTER2_CONTEXT \
      --set inferencePool.modelServers.matchLabels.app=vllm-llama3-8b-instruct \
      --set provider.name=gke \
      --set inferenceExtension.monitoring.gke.enabled=true \
      --version v1.1.0 \
      oci://registry.k8s.io/gateway-api-inference-extension/charts/inferencepool
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.
  5. Marca los recursos InferencePool como exportados en ambos clústeres. Esta anotación hace que InferencePool esté disponible para la importación por parte del clúster de configuración, que es un paso obligatorio para el enrutamiento de varios clústeres.

    kubectl annotate inferencepool vllm-llama3-8b-instruct networking.gke.io/export="True" \
        --context=CLUSTER1_CONTEXT
    
    kubectl annotate inferencepool vllm-llama3-8b-instruct networking.gke.io/export="True" \
        --context=CLUSTER2_CONTEXT
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.

Implementa recursos en el clúster de configuración

Para definir cómo se enruta y balancea la carga del tráfico en los recursos InferencePool de todos los clústeres registrados, implementa los recursos Gateway, HTTPRoute y HealthCheckPolicy. Implementas estos recursos solo en el clúster de configuración designado, que es gke-west en este documento.

  1. Crea un archivo llamado mcig.yaml con el siguiente contenido:

    ---
    apiVersion: gateway.networking.k8s.io/v1
    kind: Gateway
    metadata:
      name: cross-region-gateway
      namespace: default
    spec:
      gatewayClassName: gke-l7-cross-regional-internal-managed-mc
      addresses:
      - type: networking.gke.io/ephemeral-ipv4-address/europe-west3
        value: "europe-west3"
      - type: networking.gke.io/ephemeral-ipv4-address/us-east4
        value: "us-east4"
      listeners:
      - name: http
        protocol: HTTP
        port: 80
    ---
    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
      name: vllm-llama3-8b-instruct-default
    spec:
      parentRefs:
      - name: cross-region-gateway
        kind: Gateway
      rules:
      - backendRefs:
        - group: networking.gke.io
          kind: GCPInferencePoolImport
          name: vllm-llama3-8b-instruct
    ---
    apiVersion: networking.gke.io/v1
    kind: HealthCheckPolicy
    metadata:
      name: health-check-policy
      namespace: default
    spec:
      targetRef:
        group: "networking.gke.io"
        kind: GCPInferencePoolImport
        name: vllm-llama3-8b-instruct
      default:
        config:
          type: HTTP
          httpHealthCheck:
            requestPath: /health
            port: 8000
    
  2. Aplica el manifiesto

    kubectl apply -f mcig.yaml --context=CLUSTER1_CONTEXT
    

    Reemplaza CLUSTER1_CONTEXT por el contexto del primer clúster (el clúster de configuración), por ejemplo, gke_my-project_europe-west3-c_gke-west.

Habilita los informes de métricas personalizadas

Para habilitar los informes de métricas personalizadas y mejorar el balanceo de cargas en varias regiones, debes exportar las métricas de uso de la caché de KV de todos los clústeres. El balanceador de cargas usa estos datos de uso de la caché de KV exportados como un indicador de carga personalizado. El uso de este indicador de carga personalizado permite tomar decisiones de balanceo de cargas más inteligentes en función de la carga de trabajo real de cada clúster.

  1. Crea un archivo llamado metrics.yaml con el siguiente contenido:

    apiVersion: autoscaling.gke.io/v1beta1
    kind: AutoscalingMetric
    metadata:
      name: gpu-cache
      namespace: default
    spec:
      selector:
        matchLabels:
          app: vllm-llama3-8b-instruct
      endpoints:
      - port: 8000
        path: /metrics
        metrics:
        - name: vllm:kv_cache_usage_perc # For vLLM versions v0.10.2 and newer
          exportName: kv-cache
        - name: vllm:gpu_cache_usage_perc # For vLLM versions v0.6.2 and newer
          exportName: kv-cache-old
    
  2. Aplica la configuración de métricas a ambos clústeres:

    kubectl apply -f metrics.yaml --context=CLUSTER1_CONTEXT
    kubectl apply -f metrics.yaml --context=CLUSTER2_CONTEXT
    

    Reemplaza lo siguiente:

    • CLUSTER1_CONTEXT: Es el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.
    • CLUSTER2_CONTEXT: Es el contexto del segundo clúster, por ejemplo, gke_my-project_us-east4-a_gke-east.

Configura la política de balanceo de cargas

Para optimizar la forma en que se distribuyen tus solicitudes de inferencia de IA/AA en tus clústeres de GKE, configura una política de balanceo de cargas. Elegir el modo de balanceo adecuado ayuda a garantizar el uso eficiente de los recursos, evita la sobrecarga de clústeres individuales y mejora el rendimiento y la capacidad de respuesta generales de tus servicios de inferencia.

Configura los tiempos de espera

Si se espera que tus solicitudes tengan duraciones prolongadas, configura un tiempo de espera más largo para el balanceador de cargas. En GCPBackendPolicy, establece el campo timeoutSec en al menos el doble de la latencia de solicitud del percentil 99 estimada.

Por ejemplo, en el siguiente manifiesto, se establece el tiempo de espera del balanceador de cargas en 100 segundos.

apiVersion: networking.gke.io/v1
kind: GCPBackendPolicy
metadata:
  name: my-backend-policy
spec:
  targetRef:
    group: "networking.gke.io"
    kind: GCPInferencePoolImport
    name: vllm-llama3-8b-instruct
  default:
    timeoutSec: 100
    balancingMode: CUSTOM_METRICS
    trafficDuration: LONG
    customMetrics:
    - name: gke.named_metrics.kv-cache
      dryRun: false

Para obtener más información, consulta las limitaciones de la puerta de enlace de varios clústeres.

Debido a que los modos de balanceo de cargas Métricas personalizadas y Solicitudes en tránsito son mutuamente exclusivos, configura solo uno de estos modos en tu GCPBackendPolicy.

Elige un modo de balanceo de cargas para tu implementación.

Métricas personalizadas

Para un balanceo de cargas óptimo, comienza con un uso objetivo del 60%. Para alcanzar este objetivo, establece maxUtilization: 60 en la configuración de customMetrics de tu GCPBackendPolicy.

  1. Crea un archivo llamado backend-policy.yaml con el siguiente contenido para habilitar el balanceo de cargas basado en la métrica personalizada kv-cache:

    apiVersion: networking.gke.io/v1
    kind: GCPBackendPolicy
    metadata:
      name: my-backend-policy
    spec:
      targetRef:
        group: "networking.gke.io"
        kind: GCPInferencePoolImport
        name: vllm-llama3-8b-instruct
      default:
        balancingMode: CUSTOM_METRICS
        trafficDuration: LONG
        customMetrics:
          - name: gke.named_metrics.kv-cache
            dryRun: false
            maxUtilization: 60
    
  2. Aplica la política nueva:

    kubectl apply -f backend-policy.yaml --context=CLUSTER1_CONTEXT
    

    Reemplaza CLUSTER1_CONTEXT por el contexto del primer clúster, por ejemplo, gke_my-project-europe-west3-c-gke-west.

Solicitudes en curso

Para usar el modo de balanceo en tránsito, estima la cantidad de solicitudes en tránsito que puede controlar cada backend y configura de forma explícita un valor de capacidad.

  1. Crea un archivo llamado backend-policy.yaml con el siguiente contenido para habilitar el balanceo de cargas según la cantidad de solicitudes en tránsito:

    kind: GCPBackendPolicy
    apiVersion: networking.gke.io/v1
    metadata:
      name: my-backend-policy
    spec:
      targetRef:
        group: "networking.gke.io"
        kind: GCPInferencePoolImport
        name: vllm-llama3-8b-instruct
      default:
        balancingMode: IN_FLIGHT
        trafficDuration: LONG
        maxInFlightRequestsPerEndpoint: 1000
        dryRun: false
    
  2. Aplica la política nueva:

    kubectl apply -f backend-policy.yaml --context=CLUSTER1_CONTEXT
    

    Reemplaza CLUSTER1_CONTEXT por el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.

Verifica la implementación

Para verificar el balanceador de cargas interno, debes enviar solicitudes desde tu red de VPC, ya que los balanceadores de cargas internos usan direcciones IP privadas. Ejecuta un Pod temporal dentro de uno de los clústeres para enviar solicitudes desde tu red de VPC y verificar el balanceador de cargas interno:

  1. Inicia una sesión de shell interactiva en un Pod temporal:

    kubectl run -it --rm --image=curlimages/curl curly --context=CLUSTER1_CONTEXT -- /bin/sh
    

    Reemplaza CLUSTER1_CONTEXT por el contexto del primer clúster, por ejemplo, gke_my-project_europe-west3-c_gke-west.

  2. Desde el shell nuevo, obtén la dirección IP de la puerta de enlace y envía una solicitud de prueba:

    GW_IP=$(kubectl get gateway/cross-region-gateway -n default -o jsonpath='{.status.addresses[0].value}')
    
    curl -i -X POST ${GW_IP}:80/v1/completions -H 'Content-Type: application/json' -d '{
    "model": "food-review-1",
    "prompt": "What is the best pizza in the world?",
    "max_tokens": 100,
    "temperature": 0
    }'
    

    A continuación, se muestra un ejemplo de una respuesta correcta:

    {
      "id": "cmpl-...",
      "object": "text_completion",
      "created": 1704067200,
      "model": "food-review-1",
      "choices": [
        {
          "text": "The best pizza in the world is subjective, but many argue for Neapolitan pizza...",
          "index": 0,
          "logprobs": null,
          "finish_reason": "length"
        }
      ],
      "usage": {
        "prompt_tokens": 10,
        "completion_tokens": 100,
        "total_tokens": 110
      }
    }
    

¿Qué sigue?