从零开始的云原生之旅(十三):Ingress 深度剖析——从 Service 到统一入口

从零开始的云原生之旅(十三):Ingress 深度剖析------从 Service 到统一入口

要掌握 Ingress,必须先看懂 Kubernetes 在 L4/L7 之间的分工,再理解 Ingress 资源与 Ingress Controller 的协作方式。

📖 文章目录

  • [前言:为什么要在 Nginx 实战之前再写一篇 Ingress 文](#前言:为什么要在 Nginx 实战之前再写一篇 Ingress 文)
  • [一、回顾 Service 暴露方式:Ingress 的位置在哪?](#一、回顾 Service 暴露方式:Ingress 的位置在哪?)
  • [二、为什么需要 Ingress:从 URL 到后端的决策链路](#二、为什么需要 Ingress:从 URL 到后端的决策链路)
  • [三、Ingress 三层架构:声明、控制器、数据面](#三、Ingress 三层架构:声明、控制器、数据面)
  • [四、Ingress 资源规范全解析](#四、Ingress 资源规范全解析)
    • [4.1 元数据与 IngressClass](#4.1 元数据与 IngressClass)
    • [4.2 规则匹配:Host、Path、Backend](#4.2 规则匹配:Host、Path、Backend)
    • [4.3 PathType 与匹配策略](#4.3 PathType 与匹配策略)
    • [4.4 默认后端与 404 处理](#4.4 默认后端与 404 处理)
  • [五、IngressClass 与多控制器共存实践](#五、IngressClass 与多控制器共存实践)
  • [六、TLS 终止与证书管理](#六、TLS 终止与证书管理)
  • [七、常见注解分类:让 Ingress 更聪明](#七、常见注解分类:让 Ingress 更聪明)
  • 八、请求生命周期:一次外部访问发生了什么
  • [九、Ingress Controller 生态对比](#九、Ingress Controller 生态对比)
  • [十、Ingress 的局限与演进:何时选择 Istio](#十、Ingress 的局限与演进:何时选择 Istio)
  • 十一、实战清单:排查与最佳实践
  • [结语:为下一篇 Istio 铺路](#结语:为下一篇 Istio 铺路)

前言:为什么要在 Nginx 实战之前再写一篇 Ingress 文

在《从 Service 到 Ingress:K8s 服务暴露完全指南》中,我们站在宏观视角梳理了四种服务暴露方式;而《Ingress Controller 实战:Nginx Ingress 深度解析》则直接进入实操。很多读者反馈在动手之前仍然对 Ingress 本质资源规范 感到困惑。这篇文章正是为了解答:

  • Ingress 是什么?在哪一层起作用?
  • Ingress 资源、IngressController 与 Service 如何协作?
  • PathType、IngressClass、默认后端等规范字段到底如何使用?
  • 为什么 Ingress 做不到金丝雀、熔断?何时应该迁移到 Istio?

一、回顾 Service 暴露方式:Ingress 的位置在哪?

层级 方式 适用范围 能力 成本
L3/L4 ClusterIP 集群内部 Pod 发现、负载均衡 ✅ 低
L3/L4 NodePort 集群外部(固定端口) 暴露端口、无 L7 路由 ⚠️ 中
L3/L4 LoadBalancer 云厂商 / LB 自动申请公网负载均衡 ⚠️ 中
L7 Ingress 统一入口 基于域名/路径的应用层路由 ⚠️ 中

Ingress 不是替代 Service,而是在 LoadBalancer / NodePort 之后,提供 HTTP(S) 层的路由和策略


二、为什么需要 Ingress:从 URL 到后端的决策链路

设想一个 SaaS 平台:

text 复制代码
https://api.company.com/v1/users
https://dashboard.company.com/
https://admin.company.com/

没有 Ingress 时,我们要为每个服务单独暴露端口或者申请 LB,不仅浪费资源,也难以统一管理证书、WAF、重写等需求。Ingress 将不同域名和路径的 路由决策集中管理,所有外部请求统一先进入 Ingress,再由它决定转向哪个 Service。


三、Ingress 三层架构:声明、控制器、数据面

watch 配置下发 L7 转发 Ingress 资源
networking.k8s.io/v1 Ingress Controller
自定义控制器 数据平面
Nginx/Envoy/HAProxy Service

  1. 声明面(Ingress 资源):存储在 etcd 中的 YAML 配置,只负责描述路由规则。
  2. 控制面(Ingress Controller):监听 Ingress 资源变化,生成具体实现(例如 Nginx 配置文件)。
  3. 数据面(代理进程):真正接收请求并执行 HTTP 路由、TLS 终止等功能。

这三层缺一不可。单独创建 Ingress 资源而没有控制器,等同于写了 YAML 但无人执行。


四、Ingress 资源规范全解析

4.1 元数据与 IngressClass

yaml 复制代码
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: app-ingress
  namespace: default
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /$1
spec:
  ingressClassName: nginx  # 绑定特定控制器
  • metadata.annotations:为控制器传递特定行为,如重写、限流。
  • spec.ingressClassName:指定使用哪一个 Ingress Controller;未指定时依据默认 IngressClass。

4.2 规则匹配:Host、Path、Backend

yaml 复制代码
spec:
  rules:
  - host: api.example.com
    http:
      paths:
      - path: /v1
        pathType: Prefix
        backend:
          service:
            name: api-service
            port:
              number: 8080
  • host:域名匹配,可为空(匹配所有域)。
  • paths:同一域名下的路径规则,顺序匹配。
  • backend:最终转发到的 Service + Port。

4.3 PathType 与匹配策略

PathType 描述 典型用法
Prefix 基于前缀匹配,请求路径必须以 /v1 开头 REST API 分组
Exact 完全匹配,大小写敏感 健康检查 /healthz
ImplementationSpecific 由控制器自行定义,可能支持正则 Nginx 特有 regex

在 Kubernetes 1.22+ 中必须显式指定 pathType,避免歧义。

4.4 默认后端与 404 处理

yaml 复制代码
spec:
  defaultBackend:
    service:
      name: default-404
      port:
        number: 80

如果请求不匹配任何 rules,Ingress 会将其转发到默认后端。常见做法是部署一个返回统一 404 页面的 Service,避免泄露内部信息。


五、IngressClass 与多控制器共存实践

集群中可能同时存在多个控制器(如 Nginx、Traefik、HAProxy)。通过 IngressClass 可以显式声明使用哪一个:

yaml 复制代码
apiVersion: networking.k8s.io/v1
kind: IngressClass
metadata:
  name: nginx
spec:
  controller: k8s.io/ingress-nginx

控制器启动时会注册自己的 controller 字段,只处理匹配的 Ingress。这样我们可以:

  • 将业务流量交给 Nginx,静态文件交给 Traefik。
  • 在同一集群演练新的控制器而不影响旧流量。

六、TLS 终止与证书管理

Ingress 支持在入口处终止 TLS:

yaml 复制代码
spec:
  tls:
  - hosts:
    - app.example.com
    secretName: app-tls

关键要点:

  1. Secret 必须是 type: kubernetes.io/tls,包含 tls.crttls.key
  2. 多个域名可以共享同一个证书(SAN)。
  3. 控制器通常支持自动跳转 HTTP → HTTPS,可通过注解启用。
  4. 在多租户环境下应当使用证书管理器(如 cert-manager)自动续期。

七、常见注解分类:让 Ingress 更聪明

虽然 Ingress 规范保持精简,但控制器提供了大量注解扩展。以 Nginx 为例:

分类 代表注解 功能
重写/转发 nginx.ingress.kubernetes.io/rewrite-target URL 重写
超时/连接 nginx.ingress.kubernetes.io/proxy-read-timeout 转发超时
限流 nginx.ingress.kubernetes.io/limit-rps QPS 限制
认证 nginx.ingress.kubernetes.io/auth-url 外部鉴权
Header nginx.ingress.kubernetes.io/configuration-snippet 自定义 Nginx 片段

⚠️ 注意:注解是控制器私有的,迁移到另一种控制器时需要重新审视配置等价性。


八、请求生命周期:一次外部访问发生了什么

  1. DNSapp.example.com 解析到 LoadBalancer IP。
  2. LB 将请求发送到 Kubernetes 节点上的 Ingress Controller Service。
  3. Ingress Controller Pod 中的代理进程(Nginx/Envoy)接收请求。
  4. 代理根据缓存的配置(由 Ingress 资源生成)匹配 Host/Path。
  5. 代理与目标 Service 建立连接,并按负载均衡策略转发到 Pod。
  6. Pod 返回响应,经由代理回传给客户端。

整个过程对应用透明,应用只需暴露 ClusterIP Service。


九、Ingress Controller 生态对比

控制器 实现 优势 局限
Nginx Ingress Nginx + Lua 成熟稳定,生态庞大 配置复杂,扩展需依赖注解
Traefik Go 原生 + CRD 动态配置,内置服务发现 高级特性需要 Enterprise 版
HAProxy Ingress HAProxy 高性能,支持高级 TCP 社区相对较小
Kong Ingress Kong API Gateway 原生支持 API 网关能力 资源占用高
AWS/GCP Ingress 云厂商 LB 与云生态深度集成 绑定特定云厂商
Istio Gateway Envoy(服务网格入口) 与 Service Mesh 深度结合 依赖 Istio 体系,成本高

十、Ingress 的局限与演进:何时选择 Istio

Ingress 专注于 北向流量(North-South),无法解决以下需求:

  • 服务之间的东西向流量治理(调用链、熔断、重试、指标)。
  • 细粒度的流量切分(金丝雀、A/B 测试、镜像流量)。
  • 零信任要求下的服务间 mTLS。

当系统演进到复杂微服务拓扑时,Ingress 往往成为瓶颈,这也是我们在 v0.4 中引入 Istio 的原因:

text 复制代码
Ingress → 解决统一入口问题
Istio   → 解决服务网格治理问题

十一、实战清单:排查与最佳实践

  • 先验证控制器是否运行kubectl get pods -n ingress-nginx
  • 通过 events 排查kubectl describe ingress app-ingress 查看调度到哪个 IngressClass、是否创建成功。
  • 善用默认后端:提供统一错误页,便于观测未命中规则的流量。
  • 避免过度依赖注解:抽象复用常见配置,防止迁移困难。
  • 分环境管理证书:生产环境务必配置自动续期和审计。
  • 监控代理指标:关注连接数、响应时间、后端错误率。
  • 与 Service 策略配合:Service 的 SessionAffinity、ExternalTrafficPolicy 对链路有重要影响。

结语:为下一篇 Istio 铺路

至此,我们从概念、规范、生态和实践等维度彻底理解了 Ingress。它是进入 Kubernetes 北向流量的必经之路,却也有与生俱来的边界。下一篇《初探服务网格:Istio 让微服务更简单》将接棒,讲述如何在 Istio 中延续入口能力,并将流量治理扩展到整个微服务拓扑。

先理解好 Ingress 的角色,再拥抱 Istio,你会更清楚每一层的价值与取舍。

相关推荐
n***i952 小时前
云原生数据库使用体验,与传统数据库差异
数据库·云原生
炸裂狸花猫11 小时前
开源监控体系Prometheus & Thanos & Grafana & Alertmanager
云原生·开源·prometheus·监控·thanos
终端行者12 小时前
K8s常用排障调试工具 入侵排查 kubectl debug 命令详解
云原生·容器·kubernetes
fie888912 小时前
Kubernetes(k8s)高可用性集群的构建详细步骤
云原生·容器·kubernetes
奋斗的蛋黄12 小时前
K8s Ingress 与 Ingress API 全解析:外部访问集群的统一入口
云原生·容器·kubernetes
ghie909013 小时前
k8s节点故障修复:v1.Secret观察失败解决方案
云原生·容器·kubernetes
岚天start17 小时前
K8S中nodePort、port和 targetPort的区别
云原生·容器·kubernetes
CNRio20 小时前
软件架构趋势:云原生与大模型的融合与重塑
云原生
~kiss~20 小时前
Milvus-云原生和分布式的开源向量数据库-介绍
分布式·云原生·milvus