Aller au contenu
Conteneurs & Orchestration medium

Gateway API : routage avancé et gouvernance réseau

45 min de lecture

logo kubernetes

Gateway API est la nouvelle approche recommandée pour les besoins de routage avancés dans Kubernetes. Elle complète et dépasse les capacités d'Ingress, dont l'API reste stable mais gelée. Ce guide présente les concepts clés, les différences avec Ingress, et comment adopter Gateway API progressivement.

  • Les limitations d'Ingress et pourquoi Gateway API existe
  • Les ressources GatewayClass, Gateway, HTTPRoute et ReferenceGrant
  • La différence entre canaux Standard et Experimental
  • Créer et vérifier une configuration de routage
  • Les fonctionnalités avancées (headers, redirections, weights)
  • Quand choisir Ingress ou Gateway API

L'API Ingress date des débuts de Kubernetes et n'a plus évolué depuis sa stabilisation : tout ce qu'elle ne couvrait pas a été rajouté par les éditeurs sous forme d'annotations, propres à chaque contrôleur. Le résultat est une configuration qui ne survit pas à un changement d'implémentation. Gateway API repart de zéro avec des ressources typées et validées par l'API server, là où une annotation mal orthographiée était jusqu'ici ignorée sans le moindre message.

Gateway API n'est pas seulement "Ingress avec plus de features". C'est une manière différente d'organiser les responsabilités réseau dans Kubernetes :

  • Plus gouvernable, Séparation claire entre admin cluster, équipe plateforme et développeurs
  • Plus composable, Ressources distinctes qui s'assemblent
  • Plus standardisé, Modèle portable entre implémentations
  • Plus exigeant, Demande plus de préparation qu'Ingress

Ces limites ne sont pas des défauts d'implémentation mais des choix de conception : une ressource Ingress mélange dans un seul objet ce qui relève de l'infrastructure (ports, certificats) et ce qui relève de l'application (chemins, backends). Toute personne autorisée à créer un Ingress touche donc aux deux, ce qui interdit la délégation aux équipes de développement.

LimitationImpact
Annotations vendor-specificConfiguration non portable
Un seul niveau de configPas de séparation infra/dev
HTTP(S) uniquementPas de TCP/UDP natif
Routage basiqueManipulation headers limitée
Pas de traffic splittingCanary complexe à implémenter

La colonne de droite mérite d'être lue attentivement : Gateway API garantit la portabilité du modèle, pas celle du comportement. Un manifeste écrit pour Traefik s'applique tel quel sur Envoy Gateway, mais rien n'assure que le filtre exotique qu'il utilise soit implémenté des deux côtés. La page de conformité du projet reste la référence à consulter avant de s'engager sur une fonctionnalité.

AvantageRéalité
StandardiséLe modèle et les ressources sont portables, mais le niveau de support des fonctionnalités dépend encore de l'implémentation choisie
ExpressifRoutage avancé sans annotations propriétaires
Séparation des rôlesInfra vs développeurs clairement modélisée
Multi-protocoleHTTP, HTTPS, TCP, UDP, gRPC au niveau du modèle d'API, le support opérationnel dépend du contrôleur
ExtensiblePolicies pour rate limiting, auth, etc.

Le critère décisif n'est pas technique mais organisationnel : combien d'équipes partagent le même point d'entrée. Sur un cluster où une seule personne gère l'exposition de trois applications, Ingress fait le travail avec moins de concepts à maîtriser. Dès que plusieurs équipes publient des routes sur une infrastructure commune, la séparation des ressources devient un gain net. Les deux API cohabitent sans conflit dans un même cluster, ce qui autorise une bascule progressive.

BesoinIngressGateway API
Exposer vite une appli simple✅ Bien adapté⚠️ Possible mais plus structuré
Routage avancé multi-équipes⚠️ Limité✅ Très adapté
Politique claire infra/dev❌ Faible✅ Forte
Portabilité inter-contrôleurs⚠️ Moyenne (annotations)✅ Meilleure
Adoption dans cluster existant simple✅ Plus facile⚠️ Demande plus de préparation
Traffic splitting natif❌ Non✅ Oui
TCP/UDP/gRPC❌ Non✅ Selon contrôleur

Recommandation :

  • Nouveau projet avec besoins avancés → Gateway API
  • Projet existant stable et simple → Ingress reste acceptable
  • Besoin de gouvernance multi-équipes → Gateway API

Gateway API sépare les responsabilités en trois niveaux :

Trois niveaux de responsabilité empilés : la GatewayClass, gérée par l'administrateur du cluster, choisit l'implémentation Traefik, Envoy ou NGINX ; la Gateway, gérée par l'équipe plateforme, configure les points d'écoute (ports, TLS, domaines) ; les HTTPRoute et GRPCRoute, gérées par les développeurs, définissent le routage vers les Services

RessourceQui la gèreResponsabilité
GatewayClassCluster adminChoix du contrôleur
GatewayÉquipe plateformePorts, TLS, domaines autorisés
HTTPRouteDéveloppeursRègles de routage applicatif
ReferenceGrantÉquipe plateformeAutorise les références cross-namespace

Gateway API publie ses fonctionnalités via deux canaux :

CanalUsageStabilité
StandardProductionFonctionnalités GA, stables
ExperimentalTests, labsFonctionnalités en développement, peuvent changer

Pour connaître les fonctionnalités de chaque canal, consultez le guide Getting Started officiel.

Le déploiement se fait en deux temps, et les oublier tous les deux est l'erreur d'installation la plus fréquente. Les CRDs (Custom Resource Definitions) ajoutent les types Gateway, HTTPRoute et consorts au vocabulaire de l'API server ; le contrôleur est le programme qui lit ces objets et configure réellement un proxy. Sans contrôleur, vos ressources sont acceptées par le cluster mais aucun trafic n'est routé.

Gateway API n'est pas inclus par défaut. Installez les CRDs depuis le Standard channel :

Fenêtre de terminal
# Consultez la dernière version sur https://gateway-api.sigs.k8s.io/guides/
# Exemple avec une version récente (à adapter) :
kubectl apply -f https://github.com/kubernetes-sigs/gateway-api/releases/download/v1.6.0/standard-install.yaml
# Vérification
kubectl get crd | grep gateway

Les CRDs seuls ne suffisent pas. Vous avez besoin d'un contrôleur qui implémente Gateway API :

ContrôleurNotes
TraefikSupport complet, simple à déployer
Envoy GatewayRéférence Gateway API, très complet
NGINX Gateway FabricPerformant, support enterprise
CiliumeBPF-based, intégré au CNI
IstioService mesh complet
KongAPI Gateway avec plugins

Quatre ressources composent le modèle, et elles s'emboîtent dans un ordre imposé : une HTTPRoute ne sert à rien sans un Gateway qui l'accepte, lequel ne démarre pas sans une GatewayClass prise en charge par un contrôleur. Le ReferenceGrant s'ajoute dès qu'une référence traverse une frontière de namespace. Les manifestes qui suivent forment un ensemble cohérent, à lire dans cet ordre.

Définit l'implémentation utilisée (géré par l'admin cluster). Le champ controllerName désigne le contrôleur qui prendra en charge cette classe : c'est une chaîne fixée par l'éditeur, à reprendre exactement telle qu'elle figure dans sa documentation. Une GatewayClass est une ressource de portée cluster, elle n'appartient à aucun namespace :

gatewayclass.yaml
apiVersion: gateway.networking.k8s.io/v1
kind: GatewayClass
metadata:
name: traefik
spec:
controllerName: traefik.io/gateway-controller

Vérifiez les GatewayClass disponibles :

Fenêtre de terminal
kubectl get gatewayclass

Configure les points d'entrée (géré par l'équipe plateforme). Chaque listener décrit une combinaison port, protocole et politique d'attachement ; c'est également ici que se termine le TLS, avec mode: Terminate qui déchiffre au niveau du Gateway. La création d'un Gateway provoque en général celle d'un Service de type LoadBalancer par le contrôleur, donc l'allocation d'une adresse publique :

gateway.yaml
apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
name: main-gateway
namespace: gateway-system
spec:
gatewayClassName: traefik
listeners:
- name: http
port: 80
protocol: HTTP
allowedRoutes:
namespaces:
from: Same
- name: https
port: 443
protocol: HTTPS
tls:
mode: Terminate
certificateRefs:
- name: wildcard-cert
allowedRoutes:
namespaces:
from: Selector
selector:
matchLabels:
gateway-access: "true"

Points clés :

  • listeners, Définit les ports et protocoles
  • allowedRoutes, Contrôle quels namespaces peuvent attacher des routes
  • tls, Configuration TLS par listener

Définit les règles de routage (géré par les développeurs). Le champ parentRefs désigne le Gateway auquel la route demande à s'attacher : la demande n'aboutit que si la politique allowedRoutes du Gateway l'autorise, ce qui donne à l'équipe plateforme le dernier mot. Les hostnames déclarés ici doivent être compatibles avec ceux du listener, sans quoi la route est acceptée mais ne reçoit aucun trafic :

httproute.yaml
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: api-routes
namespace: mon-app
spec:
parentRefs:
- name: main-gateway
namespace: gateway-system
hostnames:
- "api.example.com"
rules:
- matches:
- path:
type: PathPrefix
value: /api/v1
backendRefs:
- name: api-service
port: 80
- matches:
- path:
type: PathPrefix
value: /api/v2
backendRefs:
- name: api-v2-service
port: 80

Autorise les références cross-namespace (essentiel pour la gouvernance). Par défaut, Kubernetes refuse qu'une ressource pointe vers un objet situé dans un autre namespace : sans cette autorisation explicite, n'importe quelle route pourrait monter le Secret TLS du voisin. Le ReferenceGrant se crée toujours dans le namespace qui détient l'objet convoité, ici celui du certificat, et c'est donc son propriétaire qui consent :

referencegrant.yaml
apiVersion: gateway.networking.k8s.io/v1
kind: ReferenceGrant
metadata:
name: allow-gateway-to-secret
namespace: cert-namespace
spec:
from:
- group: gateway.networking.k8s.io
kind: Gateway
namespace: gateway-system
to:
- group: ""
kind: Secret
name: wildcard-cert

Ce ReferenceGrant permet au Gateway dans gateway-system de référencer le Secret wildcard-cert dans cert-namespace.

Gateway API fournit un status riche sur chaque ressource. Utilisez-le pour diagnostiquer :

Une classe ACCEPTED: True prouve qu'un contrôleur l'a reconnue et se déclare responsable. Si la colonne reste vide ou à False, le contrôleur n'est pas installé ou le controllerName ne correspond pas au sien.

Fenêtre de terminal
kubectl get gatewayclass
# La colonne ACCEPTED doit être True

Deux conditions distinctes se suivent : Accepted signifie que la configuration est valide, Programmed que le proxy sous-jacent l'a réellement appliquée et écoute. Un Gateway Accepted mais pas Programmed traduit souvent une adresse de load balancer jamais attribuée.

Fenêtre de terminal
kubectl get gateways -A
kubectl describe gateway main-gateway -n gateway-system
# Cherchez les conditions : Accepted, Programmed

Le bloc Parents du statut est renseigné par le Gateway lui-même, ce qui en fait la preuve que l'attachement a été accepté. La condition ResolvedRefs concerne les backends : elle passe à False si un Service référencé n'existe pas ou n'expose pas le port demandé.

Fenêtre de terminal
kubectl get httproutes -A
kubectl describe httproute api-routes -n mon-app
# Cherchez : Parents (le Gateway parent) et les conditions Accepted/ResolvedRefs

C'est le problème le plus courant. Votre HTTPRoute existe mais le trafic ne passe pas.

  1. Vérifiez que le Gateway existe et est ACCEPTED

    Fenêtre de terminal
    kubectl get gateway main-gateway -n gateway-system
    # Status doit être ACCEPTED
  2. Vérifiez que l'HTTPRoute référence le bon Gateway

    Fenêtre de terminal
    kubectl describe httproute api-routes -n mon-app | grep -A5 "Parent Refs"
  3. Vérifiez les conditions de l'HTTPRoute

    Fenêtre de terminal
    kubectl describe httproute api-routes -n mon-app | grep -A10 "Status"
    # Cherchez : Accepted, ResolvedRefs
  4. Vérifiez que le namespace est autorisé

    Si le Gateway utilise allowedRoutes.namespaces.from: Selector, vérifiez que votre namespace a le bon label :

    Fenêtre de terminal
    kubectl get ns mon-app --show-labels
  5. Vérifiez que le Service backend existe

    Fenêtre de terminal
    kubectl get svc api-service -n mon-app
SymptômeCause probableSolution
HTTPRoute Accepted: FalseGateway introuvable ou mauvais namespaceVérifiez parentRefs
HTTPRoute ResolvedRefs: FalseService backend introuvableVérifiez le nom/port du Service
Gateway Programmed: FalseContrôleur pas prêtVérifiez les logs du contrôleur
Trafic ne passe pasNamespace non autoriséVérifiez allowedRoutes et labels

Les extraits qui suivent ne montrent que le bloc spec d'une HTTPRoute : ajoutez-y les parentRefs et les hostnames de votre contexte pour obtenir un manifeste applicable. Ils couvrent les cinq besoins qui reviennent en production, du simple découpage par chemin jusqu'à la réécriture d'en-têtes.

L'ordre des règles dans le fichier n'a aucune importance : la spécification impose de retenir la correspondance la plus spécifique, un chemin exact l'emportant sur un préfixe, et le préfixe le plus long sur le plus court. Inutile donc de classer vos règles de la plus fine à la plus large comme le réflexe nginx y pousse.

spec:
rules:
- matches:
- path:
type: PathPrefix
value: /users
backendRefs:
- name: users-service
port: 80
- matches:
- path:
type: PathPrefix
value: /orders
backendRefs:
- name: orders-service
port: 80

La comparaison est exacte par défaut et sensible à la casse pour la valeur, pas pour le nom de l'en-tête. Ce mécanisme sert surtout aux déploiements sombres : les testeurs positionnent l'en-tête et atteignent la version candidate, tous les autres restent sur la version stable.

spec:
rules:
- matches:
- headers:
- name: X-Version
value: "beta"
backendRefs:
- name: api-beta
port: 80
- matches:
- path:
type: PathPrefix
value: /api
backendRefs:
- name: api-stable
port: 80

Les weight ne sont pas des pourcentages mais des parts relatives : la proportion reçue par un backend vaut son poids divisé par la somme des poids de la règle. Un poids à 0 retire un backend de la répartition sans supprimer sa déclaration, ce qui permet de couper un canari en une seule modification.

spec:
rules:
- matches:
- path:
type: PathPrefix
value: /api
backendRefs:
- name: api-v1
port: 80
weight: 90
- name: api-v2
port: 80
weight: 10

Le filtre RequestRedirect répond directement au client, sans jamais joindre de backend : une règle qui l'utilise n'a donc pas besoin de backendRefs. Le statusCode accepte 301 (permanent, mis en cache par les navigateurs) ou 302, et le choix se corrige mal une fois la réponse mémorisée côté client.

spec:
rules:
- matches:
- path:
type: Exact
value: /old-page
filters:
- type: RequestRedirect
requestRedirect:
scheme: https
hostname: new.example.com
statusCode: 301

RequestHeaderModifier agit sur la requête envoyée au backend, jamais sur la réponse renvoyée au client, qui relève du filtre ResponseHeaderModifier. Retirer un en-tête interne avant de transmettre est une bonne pratique de sécurité : cela empêche un client de forger un en-tête auquel votre application ferait confiance.

spec:
rules:
- matches:
- path:
type: PathPrefix
value: /api
filters:
- type: RequestHeaderModifier
requestHeaderModifier:
add:
- name: X-Environment
value: "staging"
remove:
- X-Internal-Header
backendRefs:
- name: api-service
port: 80

Migrer ne consiste pas à convertir des fichiers un par un : un Ingress correspond à deux ressources Gateway API portées par deux équipes différentes. La bascule se fait donc application par application, en gardant les deux API actives le temps de la transition, puisqu'elles peuvent servir le même nom de domaine sur des points d'entrée distincts.

La migration depuis Ingress suppose généralement qu'une équipe plateforme ait déjà :

  1. Déployé un contrôleur compatible Gateway API
  2. Créé une GatewayClass (ou utilisé celle créée automatiquement)
  3. Publié un Gateway auquel les équipes applicatives peuvent rattacher leurs routes

Les développeurs ne "remplacent" pas juste un Ingress par un HTTPRoute, ils attachent leur route à un Gateway existant.

Ce tableau sert de grille de lecture pour traduire un manifeste existant. Les deux dernières lignes concentrent le vrai travail : ce qui vivait dans des annotations propriétaires devient un champ typé, dont le nom et la structure changent d'un contrôleur à l'autre. Toutes les annotations n'ont pas d'équivalent, certaines correspondent à des fonctionnalités encore en canal Experimental.

IngressGateway API
IngressClassGatewayClass
IngressGateway + HTTPRoute
host:HTTPRoute hostnames:
path:HTTPRoute matches.path:
backend:HTTPRoute backendRefs:
Annotations TLSGateway listeners.tls:
Annotations rewriteHTTPRoute filters.URLRewrite:

Cet exemple illustre le déplacement de responsabilité : l'annotation rewrite-target, spécifique à NGINX, devient un filtre URLRewrite standard, et tout ce qui touchait au point d'entrée disparaît du manifeste du développeur. Le fichier final est plus long mais ne contient plus rien de propriétaire.

Ingress (avant) :

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api-ingress
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /
spec:
ingressClassName: nginx
rules:
- host: api.example.com
http:
paths:
- path: /api
pathType: Prefix
backend:
service:
name: api-service
port:
number: 80

Gateway API (après) :

# L'équipe plateforme a déjà créé le Gateway
# Le développeur crée uniquement l'HTTPRoute :
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: api-route
namespace: mon-app
spec:
parentRefs:
- name: main-gateway
namespace: gateway-system
hostnames:
- "api.example.com"
rules:
- matches:
- path:
type: PathPrefix
value: /api
filters:
- type: URLRewrite
urlRewrite:
path:
type: ReplacePrefixMatch
replacePrefixMatch: /
backendRefs:
- name: api-service
port: 80

Le socle HTTP est stable et utilisable en production sans réserve ; ce sont les protocoles autres que HTTP et les politiques avancées qui restent mouvants. La mention « selon certaines implémentations » est déterminante : une ressource peut être GA dans la spécification tout en n'étant supportée par aucun contrôleur que vous envisagez. Vérifiez toujours le couple ressource et contrôleur, jamais la ressource seule.

AspectÉtat (2026)
HTTPRoute, Gateway, GatewayClassGA (Standard channel)
GRPCRoute, TLSRouteGA sur certaines implémentations
ReferenceGrantGA
TCPRoute, UDPRouteExperimental sur certaines implémentations
BackendTLSPolicyExperimental

Gateway API est en GA pour son socle principal et continue d'évoluer via les canaux Standard et Experimental. Consultez régulièrement les release notes pour suivre les nouveautés.

RessourceRôleGéré par
GatewayClassChoix implémentationAdmin cluster
GatewayListeners, TLS, namespaces autorisésÉquipe plateforme
HTTPRouteRègles de routageDéveloppeurs
ReferenceGrantAutorise références cross-namespaceÉquipe plateforme

Ce que Gateway API apporte :

  1. Gouvernance, Séparation claire des responsabilités infra/dev
  2. Portabilité, Configuration standardisée (mais vérifiez le support du contrôleur)
  3. Traffic splitting, Canary natif sans annotations
  4. Manipulation headers, Filtres intégrés
  5. Multi-protocole, HTTP, TCP, gRPC (selon implémentation)

Ce que Gateway API demande :

  1. Plus de préparation, Gateway doit exister avant les routes
  2. Vérification de conformité, Toutes les features ne sont pas supportées partout
  3. Compréhension du modèle, Plus de concepts qu'Ingress

Message clé : Ingress reste acceptable pour les cas simples. Gateway API devient le meilleur choix dès qu'on veut de la gouvernance, du routage avancé, ou une standardisation durable.

Ces questions portent sur les points qui coûtent le plus cher en pratique : le rôle de chaque ressource, les conditions de statut et les règles d'attachement entre namespaces. Un score inférieur à 70 % désigne les sections à relire avant de déployer.

Contrôle de connaissances

Validez vos connaissances avec ce quiz interactif

10 questions
8 min.
70% requis

Informations

  • Le chronomètre démarre au clic sur Démarrer
  • Questions à choix multiples, vrai/faux et réponses courtes
  • Vous pouvez naviguer entre les questions
  • Les résultats détaillés sont affichés à la fin

Lance le quiz et démarre le chronomètre

  • Pod Networking : Le chemin réseau réel entre la Gateway et les Pods de destination.
  • mTLS pod-to-pod : Le chiffrement du trafic interne, complément du TLS terminé en bordure.

Ce site vous est utile ?

Sachez que moins de 1% des lecteurs soutiennent ce site.

Je maintiens +700 guides gratuits, sans pub ni tracking. Un soutien, même symbolique, m'aide à couvrir l'hébergement et à garder ces ressources gratuites. Merci pour votre appui.

Le formulaire ne s'affiche pas ? Ouvrir Ko-fi dans un onglet.

Abonnez-vous et suivez mon actualité DevSecOps sur LinkedIn