Ingress 流量入口
第 9 章解决了集群内部访问:Service 提供稳定虚拟 IP 与 DNS。本章处理集群外流量的入口:Ingress 负责 HTTP/HTTPS 域名与路径路由并终结 TLS,Gateway API 是它的继任标准;两者都只是规则对象,真正转发流量的是对应的 Controller。
本篇目标:理解 Ingress 与 Ingress Controller 的分工,能写出生产可用的 Ingress(含 TLS),掌握常见高级路由注解,并了解 Gateway API 的三角色定位。
1. 七层流量入口与 Ingress 架构
1.1 Ingress vs Ingress Controller
Ingress(规则对象:域名、路径、TLS、后端 Service)
│
Ingress Controller(NGINX/Traefik/云 LB,真正转发流量)
│
Service → Pod
Ingress 只是规则,不会自行转发流量。集群必须有 NGINX、Traefik、云负载均衡等 Ingress Controller。创建 Ingress 之前必须确认集群中已安装对应 Controller。
1.2 为什么需要七层入口
NodePort/LoadBalancer 是四层(IP+端口)转发,无法按域名、路径区分流量。Ingress 在七层(HTTP/HTTPS)上按 host 和 path 路由到不同后端,一个入口可以承载多个域名和服务。
2. Ingress 核心配置详解
2.1 域名与路径路由
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api
namespace: learning
spec:
ingressClassName: nginx
rules:
- host: api.example.test
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: api
port:
name: http
pathType:Prefix(前缀匹配)或Exact(精确匹配);- 不写
host的 rule 匹配所有域名(兜底); ingressClassName指向集群已注册的 IngressClass。
kubectl get ingressclass # 验证 Controller 已注册
kubectl get ingress -n learning
2.2 TLS 证书
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api-tls
namespace: learning
spec:
ingressClassName: nginx
tls:
- hosts:
- api.example.com
secretName: api-tls-cert # Secret 类型必须是 kubernetes.io/tls
rules:
- host: api.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: api
port:
name: http
kubectl create secret tls api-tls-cert \
--cert=path/to/tls.crt \
--key=path/to/tls.key \
-n learning
HTTPS 链路还应有证书到期告警和自动续期(如 cert-manager)。
3. 安装 Ingress Controller
本地开发与 CI 里常用 kind 直接运行 NGINX Ingress Controller:
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/main/deploy/static/provider/kind/deploy.yaml
kubectl wait --namespace ingress-nginx \
--for=condition=ready pod \
--selector=app.kubernetes.io/component=controller \
--timeout=90s
kubectl get ingressclass
如果 ingressclass 列表为空,说明 Controller 尚未完成注册,此时创建的 Ingress 不会生效。生产环境一般不直接 apply 这份清单:云环境优先使用云厂商托管的入口(如 AWS ALB、GCP Load Balancer 等),自建集群建议用 Helm Chart 安装并管理版本。
4. 高级路由与流量切分
基础的路由与 TLS 之外,灰度发布、路径重写、限流等 HTTP 层能力大多由 Ingress Controller 以注解(annotation)形式提供。以下示例均以 NGINX Ingress Controller 为例。
4.1 金丝雀灰度发布
把一定比例的流量切到新版本后端:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api-canary
annotations:
nginx.ingress.kubernetes.io/canary: "true" # 开启金丝雀
nginx.ingress.kubernetes.io/canary-weight: "10" # 10% 流量进入金丝雀后端
spec:
ingressClassName: nginx
rules:
- host: api.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: api-canary
port:
name: http
4.2 路径重写
metadata:
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$2
spec:
ingressClassName: nginx
rules:
- host: api.example.com
http:
paths:
- path: /api(/|$)(.*)
pathType: ImplementationSpecific
backend:
service:
name: api
port:
name: http
4.3 限流
metadata:
annotations:
nginx.ingress.kubernetes.io/limit-rps: "10"
5. Gateway API:新一代 K8s 流量标准
Gateway API 是 Ingress 的继任者,提供更明确的角色分工和更强的表达能力。它定义了三个核心资源:
| 资源 | 职责 | 谁来管理 |
|---|---|---|
GatewayClass | 定义网关实现类型(如 nginx、istio) | 平台团队 |
Gateway | 一个具体的网关实例(监听端口、TLS) | 平台团队 |
HTTPRoute | 路由规则(域名、路径、后端) | 应用团队 |
# 平台团队定义 Gateway
apiVersion: gateway.networking.k8s.io/v1
kind: Gateway
metadata:
name: platform-gateway
namespace: learning
spec:
gatewayClassName: nginx
listeners:
- name: http
port: 80
protocol: HTTP
allowedRoutes:
namespaces:
from: Same
---
# 应用团队定义 HTTPRoute
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: api-route
namespace: learning
spec:
parentRefs:
- name: platform-gateway
rules:
- matches:
- path:
type: PathPrefix
value: /api
backendRefs:
- name: api
port: 80
Gateway API 将路由规则与网关基础设施解耦,平台团队负责网关实例,应用团队管理自己的路由规则。使用前务必确认集群中已部署支持 Gateway API 的 Controller。
6. 练习
练习 A
- 在 kind 集群中安装 NGINX Ingress Controller
- 创建两个后端 Service(
api与web),用一个 Ingress 按路径路由(/api→ api,/→ web) - 从宿主机用
curl验证两条路径分别到达正确后端
练习 B
- 用
openssl生成自签名证书,创建 TLS Secret - 创建带 TLS 的 Ingress,用
curl -k https://api.example.com从宿主机验证 - 配置金丝雀注解(
canary-weight: 10),连续请求观察流量分配比例