<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/"><channel><title>Kubernetes on Wilson Wu</title><link>https://wilsonwu.me/zh/tags/kubernetes/</link><description>Recent content in Kubernetes on Wilson Wu</description><generator>Hugo</generator><language>zh-CN</language><lastBuildDate>Mon, 01 Dec 2025 00:00:00 -0500</lastBuildDate><atom:link href="https://wilsonwu.me/zh/tags/kubernetes/index.xml" rel="self" type="application/rss+xml"/><item><title>Kubernetes Ingress NGINX 退役：全面迁移到 Gateway API 的方案与实践指南</title><link>https://wilsonwu.me/zh/blog/2025/ingress-to-gateway-api/</link><pubDate>Mon, 01 Dec 2025 00:00:00 -0500</pubDate><guid>https://wilsonwu.me/zh/blog/2025/ingress-to-gateway-api/</guid><description>&lt;p&gt;Kubernetes 官方在 &lt;strong&gt;2025 年 11 月 11 日&lt;/strong&gt;发布博客，正式宣布 &lt;strong&gt;Ingress NGINX 项目进入退役（Retirement）阶段&lt;/strong&gt;，并将于 &lt;strong&gt;2026 年 3 月&lt;/strong&gt;彻底停止维护。&lt;/p&gt;
&lt;p&gt;这一举措标志着 Kubernetes 在集群入口与流量管理方面正式进入 &lt;strong&gt;Gateway API 时代&lt;/strong&gt;。对于正在使用 Ingress NGINX 的团队，这不仅是一次技术升级，更是一项需要尽快规划的风险管理工作。&lt;/p&gt;</description><content:encoded><![CDATA[<p>Kubernetes 官方在 <strong>2025 年 11 月 11 日</strong>发布博客，正式宣布 <strong>Ingress NGINX 项目进入退役（Retirement）阶段</strong>，并将于 <strong>2026 年 3 月</strong>彻底停止维护。</p>
<p>这一举措标志着 Kubernetes 在集群入口与流量管理方面正式进入 <strong>Gateway API 时代</strong>。对于正在使用 Ingress NGINX 的团队，这不仅是一次技术升级，更是一项需要尽快规划的风险管理工作。</p>
<p>本文将基于 Kubernetes 官方退役公告、Gateway API 最新生态与社区最佳实践，系统介绍：</p>
<ul>
<li>为什么 Ingress NGINX 被退休？</li>
<li>Ingress 模型的根本局限与 Gateway API 的优势</li>
<li>新的推荐替代方案：Envoy Gateway（基于 Gateway API）</li>
<li>如何从 Ingress 迁移到 Gateway API（完整迁移路径）</li>
<li>关键注意事项与生产实践建议</li>
</ul>
<h2 id="ingress-nginx-为什么从-kubernetes-正式退役">Ingress NGINX 为什么从 Kubernetes 正式退役？</h2>
<p>根据官方博客（2025–11–11），Ingress NGINX 的退役原因包括：</p>
<h3 id="-1-项目长期缺乏维护者">● 1. 项目长期缺乏维护者</h3>
<p>虽然 Ingress NGINX 使用极广，但维护压力巨大，而核心维护者数量越来越少，社区贡献下滑。项目经过数月讨论，确定无法持续投入。</p>
<h3 id="-2-无法跟上-kubernetes-网络模型的发展">● 2. 无法跟上 Kubernetes 网络模型的发展</h3>
<p>Ingress 诞生于 Kubernetes 早期，仅支持 HTTP(s) 基础路由；而随着 Service Mesh、多协议服务、网关统一治理等场景爆发，Ingress 模型难以满足现代需求。</p>
<h3 id="-3-功能严重依赖-controller-私有扩展">● 3. 功能严重依赖 Controller 私有扩展</h3>
<p>如 NGINX Ingress 的大量 Annotation、Rewrite、Header 管理等，使得 Ingress 配置在不同控制器之间高度不兼容，难以形成云原生网络的统一抽象。</p>
<h3 id="-4-gateway-api-已经成熟能够全面替代">● 4. Gateway API 已经成熟，能够全面替代</h3>
<p>Gateway API 于 2023–2024 进入 GA，解决了 Ingress 的所有痛点，是 Kubernetes SIG-Network 未来 10 年的官方战略方向。</p>

<blockquote>
  <p>官方公告明确：</p>
<ul>
<li><strong>从 2026 年 3 月起将不再提供任何补丁，包括安全补丁。</strong></li>
<li>项目代码、容器镜像、Helm Chart 虽然仍可访问，但不会再更新。</li>
<li>官方建议用户“尽快迁移”。</li>
</ul>

</blockquote>
<h2 id="ingress-的局限性为什么它必须退出历史舞台">Ingress 的局限性：为什么它必须退出历史舞台？</h2>
<p>Ingress 的设计非常简单，只能做最基础的 L7 HTTP(s) 路由：</p>
<table>
	<thead>
			<tr>
					<th>能力</th>
					<th>Ingress</th>
					<th>Gateway API</th>
			</tr>
	</thead>
	<tbody>
			<tr>
					<td>Host / Path 路由</td>
					<td>✔</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>Header 匹配</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>Query 匹配</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>HTTP Method 匹配</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>流量拆分 / 灰度发布</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>多监听端口</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>TCP / UDP / gRPC 多协议</td>
					<td>❌</td>
					<td>✔</td>
			</tr>
			<tr>
					<td>多租户 / RBAC 边界</td>
					<td>弱</td>
					<td>强</td>
			</tr>
			<tr>
					<td>可扩展性</td>
					<td>Annotation 混乱且不兼容</td>
					<td>CRD 标准扩展</td>
			</tr>
	</tbody>
</table>
<p>Ingress 的能力已无法支撑现代云原生系统的需求，而且控制器之间的行为极不一致。Gateway API 的出现正是为了解决上述所有问题。</p>
<p><img alt="架构对比" loading="lazy" src="/zh/blog/2025/ingress-to-gateway-api/1-ingress-vs-gateway-api.png"></p>
<h2 id="推荐替代方案envoy-gateway--gateway-api">推荐替代方案：Envoy Gateway + Gateway API</h2>
<p>目前官方推荐的方向是：<strong>转向 Gateway API，并选择任意兼容的 Gateway 实现</strong>。</p>
<p>在众多实现中，我们推荐 <strong>Envoy Gateway</strong>，原因包括：</p>
<h3 id="1-对-gateway-api-支持最完整">1. 对 Gateway API 支持最完整</h3>
<p>完美支持 HTTPRoute / TCPRoute / GRPCRoute 这是 Ingress 无法做到的。</p>
<h3 id="2-基于-envoy-proxy性能与可扩展性行业领先">2. 基于 Envoy Proxy，性能与可扩展性行业领先</h3>
<p>Envoy 是 CNCF 毕业项目，得到大规模生产验证。</p>
<h3 id="3-社区活跃长期维护无风险">3. 社区活跃，长期维护无风险</h3>
<p>与 Ingress NGINX 的“维护者不足”相比，Envoy Gateway 是明确的长期支持项目。</p>
<h3 id="4-与-service-mesh如-istio原生兼容">4. 与 Service Mesh（如 Istio）原生兼容</h3>
<p>Gateway API 未来将成为 Service Mesh 入口的新标准。</p>
<p>换句话说：<strong>Envoy Gateway 是最稳妥的迁移目标</strong>。</p>
<p><img alt="Envoy Gateway 架构" loading="lazy" src="/zh/blog/2025/ingress-to-gateway-api/2-envoy-gateway-architecture.png"></p>
<h2 id="迁移路径从-ingress-nginx--gateway-apienvoy-gateway">迁移路径：从 Ingress NGINX → Gateway API（Envoy Gateway）</h2>
<p>大多数企业推荐采用 <strong>双栈迁移</strong>：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-text" data-lang="text"><span style="display:flex;"><span>Ingress（旧） 和 Gateway API（新） 并存 → 服务逐个迁移 → 完全切流 → 卸载 Ingress NGINX
</span></span></code></pre></div><p>以下是完整步骤。</p>
<h2 id="步骤-1安装-gateway-api-和-envoy-gateway">步骤 1：安装 Gateway API 和 Envoy Gateway</h2>
<p>安装标准 Gateway API CRD：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-bash" data-lang="bash"><span style="display:flex;"><span>kubectl apply -f https://github.com/kubernetes-sigs/gateway-api/releases/latest/download/standard-install.yaml
</span></span></code></pre></div><p>然后安装 Envoy Gateway 控制器（官方提供 Helm / YAML）。</p>
<h2 id="步骤-2创建-gateway替代-ingress-controller--loadbalancer">步骤 2：创建 Gateway（替代 Ingress Controller + LoadBalancer）</h2>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-yaml" data-lang="yaml"><span style="display:flex;"><span><span style="color:#f92672">apiVersion</span>: <span style="color:#ae81ff">gateway.networking.k8s.io/v1</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">kind</span>: <span style="color:#ae81ff">Gateway</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">metadata</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">name</span>: <span style="color:#ae81ff">main-gateway</span>
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">namespace</span>: <span style="color:#ae81ff">infra</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">spec</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">gatewayClassName</span>: <span style="color:#ae81ff">envoy</span>
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">listeners</span>:
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">http</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">port</span>: <span style="color:#ae81ff">80</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">protocol</span>: <span style="color:#ae81ff">HTTP</span>
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">https</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">port</span>: <span style="color:#ae81ff">443</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">protocol</span>: <span style="color:#ae81ff">HTTPS</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">tls</span>:
</span></span><span style="display:flex;"><span>      <span style="color:#f92672">mode</span>: <span style="color:#ae81ff">Terminate</span>
</span></span><span style="display:flex;"><span>      <span style="color:#f92672">certificateRefs</span>:
</span></span><span style="display:flex;"><span>      - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo-cert</span>
</span></span></code></pre></div><p>这相当于原来的：</p>
<ul>
<li>Ingress Controller</li>
<li>
<ul>
<li>LoadBalancer Service</li>
</ul>
</li>
<li>
<ul>
<li>TLS 配置</li>
</ul>
</li>
</ul>
<h2 id="步骤-3把-ingress-转换为-gateway-api-路由">步骤 3：把 Ingress 转换为 Gateway API 路由</h2>
<p>原 Ingress：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-yaml" data-lang="yaml"><span style="display:flex;"><span><span style="color:#f92672">apiVersion</span>: <span style="color:#ae81ff">networking.k8s.io/v1</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">kind</span>: <span style="color:#ae81ff">Ingress</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">metadata</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">spec</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">rules</span>:
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">host</span>: <span style="color:#ae81ff">demo.example.com</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">http</span>:
</span></span><span style="display:flex;"><span>      <span style="color:#f92672">paths</span>:
</span></span><span style="display:flex;"><span>      - <span style="color:#f92672">path</span>: <span style="color:#ae81ff">/</span>
</span></span><span style="display:flex;"><span>        <span style="color:#f92672">pathType</span>: <span style="color:#ae81ff">Prefix</span>
</span></span><span style="display:flex;"><span>        <span style="color:#f92672">backend</span>:
</span></span><span style="display:flex;"><span>          <span style="color:#f92672">service</span>:
</span></span><span style="display:flex;"><span>            <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo-svc</span>
</span></span><span style="display:flex;"><span>            <span style="color:#f92672">port</span>:
</span></span><span style="display:flex;"><span>              <span style="color:#f92672">number</span>: <span style="color:#ae81ff">80</span>
</span></span></code></pre></div><p>新 HTTPRoute：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-yaml" data-lang="yaml"><span style="display:flex;"><span><span style="color:#f92672">apiVersion</span>: <span style="color:#ae81ff">gateway.networking.k8s.io/v1</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">kind</span>: <span style="color:#ae81ff">HTTPRoute</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">metadata</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo</span>
</span></span><span style="display:flex;"><span><span style="color:#f92672">spec</span>:
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">parentRefs</span>:
</span></span><span style="display:flex;"><span>    - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">main-gateway</span>
</span></span><span style="display:flex;"><span>      <span style="color:#f92672">namespace</span>: <span style="color:#ae81ff">infra</span>
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">hostnames</span>:
</span></span><span style="display:flex;"><span>    - <span style="color:#e6db74">&#34;demo.example.com&#34;</span>
</span></span><span style="display:flex;"><span>  <span style="color:#f92672">rules</span>:
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">matches</span>:
</span></span><span style="display:flex;"><span>      - <span style="color:#f92672">path</span>:
</span></span><span style="display:flex;"><span>          <span style="color:#f92672">type</span>: <span style="color:#ae81ff">PathPrefix</span>
</span></span><span style="display:flex;"><span>          <span style="color:#f92672">value</span>: <span style="color:#e6db74">&#34;/&#34;</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">backendRefs</span>:
</span></span><span style="display:flex;"><span>      - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo-svc</span>
</span></span><span style="display:flex;"><span>        <span style="color:#f92672">port</span>: <span style="color:#ae81ff">80</span>
</span></span></code></pre></div><h2 id="步骤-4灰度切流可选但强烈推荐">步骤 4：灰度切流（可选但强烈推荐）</h2>
<p>Gateway API 支持权重：</p>
<div class="highlight"><pre tabindex="0" style="color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;"><code class="language-yaml" data-lang="yaml"><span style="display:flex;"><span><span style="color:#f92672">backendRefs</span>:
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo-svc-v1</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">port</span>: <span style="color:#ae81ff">80</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">weight</span>: <span style="color:#ae81ff">90</span>
</span></span><span style="display:flex;"><span>  - <span style="color:#f92672">name</span>: <span style="color:#ae81ff">demo-svc-v2</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">port</span>: <span style="color:#ae81ff">80</span>
</span></span><span style="display:flex;"><span>    <span style="color:#f92672">weight</span>: <span style="color:#ae81ff">10</span>
</span></span></code></pre></div><p>用于：</p>
<ul>
<li>灰度发布</li>
<li>蓝绿切换</li>
<li>测试新网关</li>
<li>逐步迁移流量</li>
</ul>
<p>这是 Ingress 以前必须靠 Nginx snippet 才能做到的。</p>
<h2 id="步骤-5服务逐个迁移--最终替换所有-ingress">步骤 5：服务逐个迁移 → 最终替换所有 Ingress</h2>
<p>建议迁移顺序：</p>
<ol>
<li>无状态服务</li>
<li>内部服务（非公网）</li>
<li>低风险流量</li>
<li>高风险 / 主业务</li>
<li>全局入口流量</li>
<li>完成后卸载 Ingress NGINX</li>
</ol>
<h2 id="迁移注意事项生产环境必读">迁移注意事项（生产环境必读）</h2>
<h3 id="1-annotation-不会自动迁移">1. Annotation 不会自动迁移</h3>
<p>Ingress 的 Annotation（rewrite、headers、timeouts 等）要重写为 Gateway API 的 Policy / Filter。</p>
<h3 id="2-tls-配置方式不同">2. TLS 配置方式不同</h3>
<p>Gateway API 是 Listener 层统一处理 TLS。</p>
<h3 id="3-流量切换建议逐步进行">3. 流量切换建议逐步进行</h3>
<p>不要一次性替换大量入口。</p>
<h3 id="4-建议提前半年开始迁移">4. 建议提前半年开始迁移</h3>
<p>要赶在 2026 年 3 月停止维护前完成迁移。</p>
<h2 id="总结gateway-api-是-kubernetes-入口的未来">总结：Gateway API 是 Kubernetes 入口的未来</h2>
<p>Ingress NGINX 的退役并不是坏事，而是 Kubernetes 网络体系完成演进的标志。</p>
<p><strong>Ingress → Gateway API</strong>
是必然趋势，也是一次全面升级：</p>
<ul>
<li>更强的路由能力</li>
<li>更清晰的多租户设计</li>
<li>更丰富的现代云原生场景支持</li>
<li>更长期的社区维护保障</li>
</ul>
<p>对于已经依赖 Ingress NGINX 的团队，<strong>现在就应该开始迁移规划</strong>。</p>
<p>Gateway API + Envoy Gateway 是当前生态最稳、最现代、最推荐的方案。</p>
]]></content:encoded></item></channel></rss>