Kubernetes Gateway API 教程:从入门到精通 – wiki词典

文章标题:Kubernetes Gateway API 教程:从入门到精通

引言

在 Kubernetes 生态系统中,管理进出集群的流量一直是核心挑战之一。传统的 Ingress API 在满足日益复杂的流量管理需求时逐渐显现出局限性。为了应对这些挑战,Kubernetes SIG-NETWORK 社区推出了下一代流量管理 API——Kubernetes Gateway API。它旨在提供一个更具表现力、可扩展性和角色感知的解决方案,以标准化集群内外部流量的入口管理。

Gateway API 通过引入一种以角色为中心的设计理念,清晰地划分了基础设施提供商、集群操作员和应用开发者之间的职责,从而实现了更灵活、更强大的流量管理能力。本教程将带您从零开始,逐步深入了解 Kubernetes Gateway API 的核心概念、安装配置、基本用法,直至掌握其高级流量管理功能和强大的可扩展性。


第一部分:入门篇 – 理解核心概念

1. 什么是 Kubernetes Gateway API?

Kubernetes Gateway API 是一个声明式的、面向角色的 API 集合,用于管理 Kubernetes 集群的南北向(外部到集群)和东西向(集群内部)流量。它被设计为 Ingress API 的继任者,旨在解决 Ingress 在多协议支持、可扩展性、多租户和高级流量管理方面的不足。

Gateway API 与 Ingress API 的对比:

特性 Ingress API Gateway API
设计理念 单一资源模型,职责混淆 角色分离 (提供商、操作员、开发者)
协议支持 主要限于 HTTP/HTTPS 支持 HTTP/HTTPS, TCP, UDP, TLS 嗅探等多种协议
可扩展性 严重依赖控制器注解 (Annotations) 内置丰富的扩展点,通过 CRD 实现,无需注解
多租户支持 有限,通常需要额外工具或复杂配置 原生支持多租户,通过 GatewayReferenceGrant 明确划分权限
流量管理 功能较少,高级功能依赖控制器实现 内置更丰富的流量管理能力,如加权流量拆分、流量镜像、URL 重写等
资源模型 Ingress GatewayClass, Gateway, HTTPRoute, TCPRoute, UDPRoute, TLSRoute

2. 核心资源:GatewayClass, Gateway, Routes

Gateway API 引入了几个新的自定义资源 (CRD),它们共同协作来定义和管理流量:

  • GatewayClass:

    • 定义: GatewayClass 类似于 StorageClassIngressClass,它定义了 Gateway 控制器的类型和通用行为。
    • 角色: 通常由基础设施提供商(如云服务商、网络团队)管理,用来声明可用的 Gateway 实现。
    • 示例: 一个 GatewayClass 可以指定使用 NGINX、Envoy、Traefik 或 Cilium 等作为底层 Gateway 控制器。
  • Gateway:

    • 定义: Gateway 资源是集群中实际的网络入口点,它代表了一个负载均衡器或代理实例。它定义了监听器 (Listeners),包括协议、端口、主机名以及 TLS 配置。
    • 角色: 由集群操作员管理,负责在集群中部署和配置具体的 Gateway 实例。一个 Gateway 可以由多个 Route 资源引用。
    • 示例: 一个 Gateway 可以配置在 80 端口监听 HTTP 流量,在 443 端口监听 HTTPS 流量。
  • 路由资源 (Route Resources):

    • 定义: 路由资源定义了从 Gateway 到后端服务的流量转发规则。Gateway API 提供了多种路由类型来处理不同协议的流量。
    • 角色: 主要由应用开发者管理,他们定义如何将特定请求路由到自己的服务。
    • 主要类型:
      • HTTPRoute: 用于定义 HTTP/HTTPS 流量的路由规则,包括基于主机名、路径、Header、Query 参数的匹配,以及流量拆分、URL 重写等。
      • TCPRoute: 用于定义原始 TCP 连接的路由规则。
      • UDPRoute: 用于定义 UDP 数据报的路由规则。
      • TLSRoute: 用于定义 TLS 加密连接的路由规则,可以在 Gateway 终止 TLS 后将流量转发到后端,或者进行 TLS 直通。

3. 安装 Gateway API

要开始使用 Gateway API,您需要完成两个主要步骤:安装 Gateway API 的 CRD 和部署一个兼容的 Gateway 控制器。

步骤 1:安装 Gateway API CRD
Gateway API 的核心抽象是通过 Kubernetes Custom Resource Definitions (CRDs) 实现的,这些 CRD 默认不会安装在 Kubernetes 集群中。

“`bash

请务必访问 Gateway API 官方文档 (gateway-api.sigs.k8s.io) 获取最新的稳定版本安装链接

kubectl apply -f https://github.com/kubernetes-sigs/gateway-api/releases/download/v1.0.0/standard-install.yaml
“`
安装完成后,您可以通过以下命令验证 CRD 是否已成功部署:

bash
kubectl get crds | grep gateway

步骤 2:部署 Gateway 控制器
Gateway API 只是一个规范,它本身不提供流量代理功能。您需要部署一个实现了 Gateway API 规范的 Gateway 控制器。目前有许多流行的实现,例如 NGINX Gateway Fabric, Envoy Gateway, Traefik, Cilium, Istio 等。

以 NGINX Gateway Fabric 为例(具体安装步骤请参照其官方文档):

“`bash

示例:通过 Helm 安装 NGINX Gateway Fabric (具体命令可能因版本而异)

helm upgrade –install nginx-gateway-fabric nginx-stable/nginx-gateway-fabric –create-namespace –namespace nginx-gateway
“`
部署完成后,您会看到相应的 Pod 运行在您指定的命名空间中。

4. 基本 HTTP 路由示例

接下来,我们将通过一个简单的示例来演示如何使用 Gateway API 暴露一个 HTTP 服务。

步骤 1:部署示例应用
首先,部署一个简单的 NGINX 应用作为后端服务。

“`yaml

app.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
name: my-nginx
spec:
selector:
matchLabels:
app: my-nginx
replicas: 2
template:
metadata:
labels:
app: my-nginx
spec:
containers:
– name: nginx
image: nginx:latest
ports:
– containerPort: 80


apiVersion: v1
kind: Service
metadata:
name: my-nginx-service
spec:
selector:
app: my-nginx
ports:
– protocol: TCP
port: 80
targetPort: 80
``
应用配置:
kubectl apply -f app.yaml`

步骤 2:定义 GatewayClass
这告诉 Kubernetes 我们将使用哪个控制器来处理流量。

“`yaml

gatewayclass.yaml

apiVersion: gateway.networking.k8s.io/v1
kind: GatewayClass
metadata:
name: my-nginx-gatewayclass
spec:
controllerName: gateway.nginx.org/nginx-gateway-controller # 替换为您的控制器名称
``
应用配置:
kubectl apply -f gatewayclass.yaml`

步骤 3:创建 Gateway
创建实际的流量入口,监听 80 端口。

“`yaml

gateway.yaml

apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
name: my-gateway
spec:
gatewayClassName: my-nginx-gatewayclass
listeners:
– name: http
protocol: HTTP
port: 80
allowedRoutes:
namespaces:
from: All # 允许所有命名空间的路由附加到此 Gateway
``
应用配置:
kubectl apply -f gateway.yaml等待Gateway被控制器成功配置并获取一个外部 IP 地址 (LoadBalancer IP 或 NodePort)。您可以通过kubectl get gateway my-gateway -o wide` 查看状态。

步骤 4:定义 HTTPRoute
定义路由规则,将来自 my-gateway 的流量转发到 my-nginx-service

“`yaml

httproute.yaml

apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: my-nginx-route
spec:
parentRefs:
– name: my-gateway # 引用之前创建的 Gateway
hostnames:
– “example.com” # 替换为您的域名,或 Gateway 的 IP 地址进行本地测试
rules:
– backendRefs:
– name: my-nginx-service
port: 80
``
应用配置:
kubectl apply -f httproute.yaml`

现在,如果您将 example.com 解析到 my-gateway 的外部 IP 地址,访问 http://example.com 应该会显示 NGINX 的欢迎页面。


第二部分:进阶篇 – 高级流量管理

Gateway API 不仅仅是 Ingress 的替代品,它还提供了丰富的高级流量管理功能。

1. 高级 HTTP 路由

HTTPRoute 资源支持复杂的匹配规则和流量处理能力。

  • 基于路径的路由 (Path-based Routing):
    根据请求的 URL 路径将流量路由到不同的后端服务。

    “`yaml

    httproute-path.yaml

    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
    name: path-route
    spec:
    parentRefs:
    – name: my-gateway
    hostnames:
    – “example.com”
    rules:
    – matches:
    – path:
    type: PathPrefix # 路径前缀匹配
    value: /app1
    backendRefs:
    – name: service-app1
    port: 80
    – matches:
    – path:
    type: Exact # 精确路径匹配
    value: /app2
    backendRefs:
    – name: service-app2
    port: 80
    “`

  • 基于 Header 和 Query Parameter 的匹配 (Header and Query Parameter Matching):
    根据 HTTP 请求的 Header 或 Query Parameter 进行流量路由,适用于 A/B 测试、功能发布等场景。

    “`yaml

    httproute-header-query.yaml

    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
    name: header-query-route
    spec:
    parentRefs:
    – name: my-gateway
    hostnames:
    – “example.com”
    rules:
    – matches:
    – headers:
    – name: X-Version
    value: v2 # 匹配 Header “X-Version: v2”
    – queryParams:
    – name: debug
    value: “true” # 匹配 Query Parameter “debug=true”
    backendRefs:
    – name: service-v2
    port: 80
    – backendRefs: # 默认路由
    – name: service-v1
    port: 80
    “`

  • URL 重写 (URL Rewriting):
    在将请求转发到后端服务之前,修改请求的 URL。这对于保持后端服务的简单性或统一入口路径非常有用。

    “`yaml

    httproute-rewrite.yaml

    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
    name: rewrite-route
    spec:
    parentRefs:
    – name: my-gateway
    hostnames:
    – “example.com”
    rules:
    – matches:
    – path:
    type: PathPrefix
    value: /old-path
    filters:
    – type: URLRewrite
    urlRewrite:
    path:
    type: ReplacePrefixMatch # 将 ‘/old-path’ 替换为 ‘/new-path’
    replacePrefixMatch: /new-path
    backendRefs:
    – name: my-nginx-service
    port: 80
    “`

2. 流量管理策略

除了路由,Gateway API 还支持更精细的流量控制。

  • 流量拆分 (加权路由 – Traffic Splitting / Weighted Routing):
    按比例将流量分发到多个后端服务,非常适用于蓝绿部署、金丝雀发布和 A/B 测试。

    “`yaml

    httproute-split.yaml

    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
    name: traffic-split-route
    spec:
    parentRefs:
    – name: my-gateway
    hostnames:
    – “example.com”
    rules:
    – backendRefs:
    – name: service-v1
    port: 80
    weight: 90 # 90% 的流量到 service-v1
    – name: service-v2
    port: 80
    weight: 10 # 10% 的流量到 service-v2
    “`

  • 流量镜像 (Traffic Mirroring):
    将一份生产流量的副本发送到另一个服务进行测试或调试,而不会影响主流量。这对于在生产环境中测试新版本或进行故障排查非常有用。

    “`yaml

    httproute-mirror.yaml

    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
    name: traffic-mirror-route
    spec:
    parentRefs:
    – name: my-gateway
    hostnames:
    – “example.com”
    rules:
    – filters:
    – type: RequestMirror
    requestMirror:
    backendRef:
    name: mirror-service # 流量副本发送到 mirror-service
    port: 80
    backendRefs:
    – name: primary-service # 主流量发送到 primary-service
    port: 80
    “`

3. TLS/HTTPS 终止

Gateway API 提供了简洁的方式来配置 HTTPS 监听器并进行 TLS 终止。

“`yaml

gateway-https.yaml

apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
name: my-https-gateway
spec:
gatewayClassName: my-nginx-gatewayclass
listeners:
– name: https
protocol: HTTPS
port: 443
hostname: “secure.example.com”
tls:
mode: Terminate # 在 Gateway 层面终止 TLS
certificateRefs:
– kind: Secret
name: my-tls-secret # 引用包含 TLS 证书和私钥的 Kubernetes Secret
allowedRoutes:
namespaces:
from: All
``my-tls-secret应该是一个类型为kubernetes.io/tls的 Secret,包含tls.crttls.key`。

4. 跨命名空间路由与 ReferenceGrant

在多租户或团队协作的环境中,通常需要允许一个命名空间中的 Route 资源引用另一个命名空间中的 Gateway 资源。ReferenceGrant 资源正是为此目的而设计,它提供了一种安全的方式来实现跨命名空间引用。

“`yaml

referencegrant.yaml

apiVersion: gateway.networking.k8s.io/v1beta1
kind: ReferenceGrant
metadata:
name: allow-routes-from-app-namespace
namespace: gateway-namespace # Gateway 所在的命名空间
spec:
from: # 允许哪些资源引用
– group: gateway.networking.k8s.io
kind: HTTPRoute
namespace: app-namespace # 允许来自 ‘app-namespace’ 的 HTTPRoute
to: # 被引用的资源
– group: gateway.networking.k8s.io
kind: Gateway
name: my-gateway # 允许引用 ‘my-gateway’
``
这个
ReferenceGrant允许app-namespace中的HTTPRoute附加到gateway-namespace中的my-gateway`。这极大地增强了 Gateway API 的多租户能力和安全性。


第三部分:精通篇 – 可扩展性与复杂场景

Gateway API 的设计哲学强调可扩展性,使其能够适应各种复杂的网络拓扑和业务需求。

1. 策略附件 (Policy Attachment)

Gateway API 通过其策略附件模型,允许将额外的配置(如限流、认证、WAF 规则)附加到 Gateway API 资源上(GatewayClass, Gateway, Route)。虽然核心 API 尚未标准化这些策略本身,但控制器通常会通过自定义 CRD 来实现这些功能。

示例 (概念性,具体实现取决于控制器):

“`yaml

rate-limit-policy.yaml

apiVersion: example.com/v1alpha1 # 这是控制器特定的 API 版本和组
kind: RateLimitPolicy
metadata:
name: global-rate-limit
spec:
targetRef: # 目标 Gateway API 资源
group: gateway.networking.k8s.io
kind: Gateway
name: my-gateway
rules:
– limit: 100 # 每秒 100 个请求
period: 1s
“`
这种机制使得 Gateway API 能够与更高级的网络功能无缝集成,同时保持核心 API 的简洁性。

2. 自定义资源与可扩展性

Gateway API 明确定义了扩展点,允许供应商和社区通过自定义资源来添加新功能或提供更细粒度的控制,而无需修改核心 API。这意味着您可以根据自己的需求,创建与 Gateway API 资源集成的自定义路由类型、过滤器或策略。

3. 与服务网格的集成

Gateway API 可以与服务网格(如 Istio, Linkerd, Consul Connect)协同工作,形成一个完整的流量管理解决方案。
* Gateway API: 通常负责南北向流量,即从集群外部进入集群的流量。它作为集群的统一入口,处理外部客户端的请求。
* 服务网格: 通常负责东西向流量,即集群内部服务间的流量。它提供服务发现、负载均衡、认证、授权、可观测性等功能。

一些服务网格甚至可以直接作为 Gateway API 的控制器,从而实现对南北向和东西向流量的统一管理,极大地简化了网络架构。

4. TCPRoute, UDPRoute, TLSRoute 的应用

除了 HTTPRoute,Gateway API 还提供了处理非 HTTP 流量的专用路由类型:

  • TCPRoute: 当您需要将原始 TCP 连接路由到后端服务时使用,例如数据库连接、自定义协议服务等。
  • UDPRoute: 用于路由 UDP 数据报,适用于 DNS、NTP 或其他基于 UDP 的服务。
  • TLSRoute: 用于处理 TLS 加密流量。它允许在 Gateway 层面终止 TLS(然后将解密后的流量转发到后端),或者进行 TLS 直通 (TLS Passthrough),将加密流量直接转发到后端服务,由后端服务处理 TLS 握手。

这些路由类型遵循与 HTTPRoute 类似的模式,通过 parentRefs 附加到 Gateway 的监听器,并通过 backendRefs 将流量转发到后端服务。

5. 多租户与 RBAC

Gateway API 的角色导向设计天然支持多租户环境和精细的 RBAC 控制:
* 基础设施提供商: 管理 GatewayClass 资源,决定哪些类型的 Gateway 控制器可用。
* 集群操作员: 基于 GatewayClass 创建 Gateway 实例,定义流量入口和监听器。他们可以通过 allowedRoutes 字段精确控制哪些命名空间的路由可以附加到他们的 Gateway 上。
* 应用开发者: 在各自的命名空间中创建 HTTPRoute(或其他路由)资源,并将其附加到被允许使用的 Gateway 上。

这种职责分离,结合 Kubernetes RBAC,使得不同的团队和用户只能配置其被授权的流量管理组件,从而实现了高度安全和隔离的多租户平台。


结论

Kubernetes Gateway API 是 Kubernetes 网络领域的一项重大进步。它通过提供一个更富有表现力、更可扩展、更具角色意识的 API,极大地提升了集群流量管理的灵活性和效率。从基础的 HTTP 路由到复杂的流量拆分、镜像,再到与服务网格的集成以及强大的多租户支持,Gateway API 为构建现代、可伸缩和安全的云原生应用提供了坚实的基础。

随着 Gateway API 的不断成熟和广泛采纳,它必将成为 Kubernetes 流量管理的首选方案,帮助企业更好地驾驭复杂的微服务架构。掌握 Gateway API,意味着您将拥有构建更强大、更灵活 Kubernetes 网络的能力。

滚动至顶部