Eseguire la migrazione di Ingress all'API Gateway

Questa pagina mostra come eseguire la migrazione della gestione del traffico su Google Kubernetes Engine (GKE) dall'API Ingress all'API Gateway. L'API Gateway fornisce una soluzione completamente gestita Google Cloud per la gestione del traffico delle applicazioni.

Per ridurre al minimo i tempi di inattività e mitigare i rischi, l'approccio più efficace per eseguire la migrazione all'API Gateway è eseguire contemporaneamente le configurazioni dell'API Ingress esistente e della nuova API Gateway. Questo metodo consente di testare in modo approfondito la nuova configurazione del gateway in un ambiente live senza influire sui servizi attuali. Dopo aver convalidato la nuova configurazione del gateway, puoi eseguire un rapido cutover DNS per reindirizzare il traffico all'API Gateway e contribuire a garantire una transizione fluida e a basso rischio.

A livello generale, la strategia di migrazione prevede le seguenti fasi:

  1. Configura il nuovo bilanciatore del carico.
  2. Definisci le regole per la gestione del traffico in entrata.
  3. Esegui il deployment della nuova configurazione e testa il flusso di traffico verso il nuovo indirizzo IP del gateway.
  4. Passa il traffico di produzione all'API Gateway.
  5. Esegui la pulizia delle risorse Ingress rimanenti.

Configura il nuovo bilanciatore del carico

In questa fase, esegui il deployment di una risorsa Gateway Kubernetes per bilanciare il carico del traffico verso il cluster GKE. Quando esegui il deployment di una risorsa Gateway, GKE configura un bilanciatore del carico delle applicazioni di livello 7 per esporre il traffico HTTP(S) alle applicazioni eseguite nel cluster. Esegui il deployment di una risorsa Gateway per ogni cluster o per ogni bilanciatore del carico di cui hai bisogno.

Nell'esempio seguente, configurerai un bilanciatore del carico delle applicazioni esterno globale. Per creare un gateway, salva il seguente manifest come gateway.yaml:

kind: Gateway
apiVersion: gateway.networking.k8s.io/v1
metadata:
  name: external-http-gateway
spec:
  gatewayClassName: gke-l7-global-external-managed # GKE's managed external Application Load Balancer
  listeners:
  - name: http
    protocol: HTTP
    port: 80
    allowedRoutes:
      namespaces:
        from: Same # Only allow HTTPRoutes from the same namespace

Il manifest precedente descrive un gateway che include i seguenti campi:

  • gatewayClassName: gke-l7-global-external-managed: specifica la classe GatewayClass per questo gateway. Questa classe Gateway utilizza un bilanciatore del carico delle applicazioni esterno globale.
  • protocol: HTTP e port: 80: specificano che il gateway espone la porta 80 per il traffico HTTP.

Definisci le regole per il traffico in entrata

Le risorse Route definiscono regole specifiche per il protocollo per mappare il traffico da un gateway ai servizi di backend.

In questa fase, traduci il manifest Ingress in una risorsa HTTPRoute. Per convertire il manifest Ingress, segui i passaggi dello strumento ingress2gateway.

Questo esempio presuppone che tu abbia la seguente risorsa Ingress:

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: cafe-ingress
spec:
  ingressClassName: nginx
  rules:
  - host: cafe.example.com
    http:
      paths:
      - path: /tea
        pathType: Prefix
        backend:
          service:
            name: tea-svc
            port:
              number: 80
      - path: /coffee
        pathType: Prefix
        backend:
          service:
            name: coffee-svc
            port:
              number: 80

Dopo aver convertito il manifest utilizzando lo strumento ingress2gateway, l'output è il manifest HTTPRoute tradotto.

Salva il seguente manifest di esempio come httproute.yaml:

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
  name: cafe-route
spec:
  # This route attaches to our new Gateway
  parentRefs:
  - name: external-http-gateway
  # The hostname is the same as before
  hostnames:
  - "cafe.example.com"
  # The routing rules are now more explicit
  rules:
  - matches:
    - path:
        type: PathPrefix
        value: /tea
    backendRefs:
    - name: tea-svc
      port: 80
  - matches:
    - path:
        type: PathPrefix
        value: /coffee
    backendRefs:
    - name: coffee-svc
      port: 80

Tieni presente che il campo rules nel manifest HTTPRoute corrisponde direttamente alle regole di instradamento definite nel manifest Ingress originale.

Esegui il deployment e testa la nuova configurazione

In questa fase, applichi i manifest Gateway e HTTPRoute che hai creato nelle due fasi precedenti e verifichi che il traffico venga indirizzato al nuovo indirizzo IP del gateway.

  1. Applica i manifest Gateway e HTTPRoute:

    kubectl apply -f gateway.yaml
    kubectl apply -f httproute.yaml
    
  2. Ottieni l'indirizzo IP del gateway. L'allocazione dell'indirizzo IP potrebbe richiedere alcuni minuti:

    kubectl get gateway external-http-gateway -o=jsonpath="{.status.addresses[0].value}" --watch
    

    L'output è l'indirizzo IP esterno del gateway, ad esempio 203.0.113.90.

  3. Testa il nuovo indirizzo IP del gateway. Utilizza il seguente comando curl per inviare una richiesta all'indirizzo IP e specificare il nome host cafe.example.com. Ad esempio:

    curl --resolve cafe.example.com:80:203.0.113.90 http://cafe.example.com/tea
    curl --resolve cafe.example.com:80:203.0.113.90 http://cafe.example.com/coffee
    

    Sostituisci 203.0.113.90 con l'indirizzo IP esterno ottenuto dal passaggio precedente. L'output conferma che il nuovo indirizzo IP del gateway instrada correttamente il traffico per cafe.example.com senza eseguire una ricerca DNS.

Indirizza il traffico al nuovo indirizzo IP del gateway

In questa fase, esegui il cutover del traffico in tempo reale dal tuo Ingress precedente al nuovo Gateway aggiornando i record DNS in modo che puntino al nuovo indirizzo IP del Gateway. I passaggi esatti per aggiornare i record DNS variano a seconda del provider DNS.

Ad esempio, se hai configurato cafe.example.com in Ingress, devi individuare il record A per cafe.example.com presso il tuo provider DNS e modificare il valore del vecchio indirizzo IP di Ingress in 203.0.113.90, che è il nuovo indirizzo IP del gateway.

Dopo aver aggiornato il record DNS, il traffico inizia a spostarsi da Ingress al gateway, ma il passaggio non avviene immediatamente per tutti i client. I resolver DNS che hanno memorizzato nella cache il record precedente attendono la scadenza del valore TTL (Time to Live) del record prima di eseguire nuovamente la query per il record e ricevere l'indirizzo IP aggiornato. Per questo motivo, devi continuare a eseguire l'Ingress esistente e il nuovo Gateway in parallelo finché non verifichi che il traffico verso l'Ingress è cessato, il che indica che la propagazione DNS è completa e i client non vengono più indirizzati al vecchio indirizzo IP. Puoi verificarlo monitorando il traffico sul bilanciatore del carico o sul controller Ingress. Per saperne di più, consulta Controllo della propagazione DNS.

Se utilizzi Cloud DNS, puoi utilizzare i pesi dei target per spostare gradualmente il traffico dal vecchio indirizzo IP al nuovo. Per saperne di più, consulta Configura le policy di routing DNS e i controlli di integrità.

Esegui la pulizia delle risorse Ingress rimanenti

Dopo aver verificato che il nuovo gateway viene eseguito correttamente, pulisci le risorse Ingress precedenti.

  1. Elimina la risorsa Ingress:

    kubectl delete ingress cafe-ingress
    
  2. Disinstalla il controller ingress-nginx. Ad esempio, se hai utilizzato Helm per installare il controller, esegui questo comando:

    helm uninstall ingress-nginx -n ingress-nginx
    

Confronto delle funzionalità tra Ingress NGINX e gateway GKE

L'API Gateway fornisce un modo più standardizzato per configurare l'ingresso e ha la parità di funzionalità per le funzionalità più comuni come il routing, le intestazioni e la suddivisione del traffico.

La tabella seguente mette a confronto la configurazione utilizzata per le funzionalità comuni nel controller Ingress e nell'API Gateway.

Funzionalità Annotazione in Ingress Configurazione nel gateway GKE Parità
Routing basato sull'host Il campo spec.rules.host nell'oggetto Ingress. Il campo hostnames nell'oggetto HTTPRoute. Parità totale.
Routing basato su percorso Il campo spec.rules.http.paths nell'oggetto Ingress e l'annotazione nginx.ingress.kubernetes.io/use-regex per la corrispondenza del percorso con espressioni regolari. Il campo rules.matches.path nell'oggetto HTTPRoute. Parità totale. Il gateway GKE supporta la corrispondenza esatta, con prefisso e con espressione regolare (RegularExpression) per i percorsi. Inoltre, puoi trovare corrispondenze con le intestazioni HTTP (rules.matches.headers) e parametri di ricerca (rules.matches.queryParams) utilizzando valori esatti o espressioni regolari.
Suddivisione del traffico nginx.ingress.kubernetes.io/canary annotazioni. HTTPRoute con il campo backendRefs ponderato. Parità totale. Inoltre, puoi suddividere il traffico con un controllo granulare.
Affinità di sessione Annotazioni nginx.ingress.kubernetes.io/affinity e nginx.ingress.kubernetes.io/affinity-mode. GCPTrafficDistributionPolicy con il campo sessionAffinity. Parità totale. Il gateway GKE supporta più tipi di affinità sessione, inclusi i tipi di affinità basati su cookie (HTTP_COOKIE, GENERATED_COOKIE e STRONG_COOKIE_AFFINITY stateful), l'affinità basata su intestazione (HEADER_FIELD) e l'affinità basata su IP client (CLIENT_IP).
CORS (Cross-Origin Resource Sharing) nginx.ingress.kubernetes.io/enable-cors HTTPRoute con un filtro CORS. Parità totale. Nota: il gateway GKE impone limiti al numero di pattern con caratteri jolly che puoi definire per listener o nome host
Riscritture URL nginx.ingress.kubernetes.io/rewrite-target HTTPRoute con un filtro urlRewrite o GCPHTTPFilter con il campo spec.urlRewrite.regexModifier. Parità totale. Il gateway GKE supporta sostituzioni di percorsi completi, sostituzioni di prefissi e riscritture di percorsi con espressioni regolari.
Manipolazione delle intestazioni nginx.ingress.kubernetes.io/proxy-set-headers o add-headers HTTPRoute con un modificatore requestHeaderModifier o un filtro responseHeaderModifier. Parità totale.
Autenticazione nginx.ingress.kubernetes.io/auth-url per l'autenticazione esterna.
  • Identity-Aware Proxy (IAP): risorsa personalizzata GCPBackendPolicy.
  • Altro: richiede un approccio più personalizzato, possibilmente con mesh di servizi o filtri personalizzati.
Parità parziale. Identity-Aware Proxy è il modo consigliato per proteggere il gateway ed è configurato sul backend.

Passaggi successivi