设计与架构 · 01 sidecar 会消失吗:从 Istio ambient GA 到 AWS App Mesh 关停,一次服务网格数据面的重新洗牌

过去半年,三件事几乎同时发生。

AWS 官方文档挂出了终止支持通知:Amazon App Mesh 将于 2026 年 9 月 30 日停止支持,之后连控制台和资源都访问不了,官方给出的迁移路径是 Amazon ECS Service Connect。Kubernetes 1.33 把 sidecar 容器从「要靠 postStart 钩子和 init 容器链硬凑出来的模式」升级成了一等原语。Istio 1.32 在 2026 年 11 月 9 日发布,第一次让 ambient 和 sidecar 混部的集群共用同一个东西向网关。

11 年前 Kubernetes 官方博客描述「组合容器」时,sidecar 只是一个模式。现在它分出了三条完全不同的实现路线,而其中一条刚刚被最大的云厂商亲手放弃。

所以这篇文章要回答的不是「sidecar 好不好」,而是你的集群该走哪条路。

一、结论先行

sidecar 模式会留下来,但「每个 Pod 塞一个 Envoy」不再是默认答案。

这三件事必须拆开看,混在一起就会得出错误结论:

层面 2026 年的状态
sidecar 作为 Kubernetes 原语 已经赢了------K8s 1.33 起原生支持,不再需要 hack
每 Pod 一个代理作为默认数据面 正在输------ambient GA、混合网格打通、云厂商收缩
sidecar 作为实现手段 不会消失------Istio 官方明确承诺,ambient 自己也需要 waypoint 这个 Envoy

Istio 官方在 ambient GA 的博客里写得很直白:

Sidecars are not going away, and remain first-class citizens in Istio.

这句话既是承诺也是警告------ambient 不是用来消灭 sidecar 的,是用来给 sidecar 减负的。想清楚这一点,后面的选型就简单了。

二、账单:sidecar 的成本写在 Istio 自己的博客里

不用去猜。在 Istio 官方宣布 ambient GA 的那篇博客里,Istio 自己列出了用户反馈的三条痛点(原文大意):

  1. sidecar 装上之后反而把应用搞坏了------注入和生命周期编排带来的兼容性问题;
  2. 每个工作负载都要背一份代理的 CPU 和内存开销;
  3. 每次 Istio 发新版本,都得把应用 Pod 重启一遍。

第二条是结构性的,也是最要命的。因为 sidecar 的总成本不是一个常数,而是:

复制代码
sidecar 总开销 ≈ 单个代理的资源占用 × Pod 副本数 × 服务数

10 个服务、平均每服务 3 个副本,就是 30 份 Envoy 常驻内存------而这些副本在低峰期大部分是空转的 。Istio 自己的说法是「large CPU and memory requirement for a proxy with every workload」,它没有给一个统一的 MB 数字,因为这个数字随 Envoy 版本、配置复杂度、启用的 filter 数量浮动,但成本模型的形状是确定的:乘以副本数。

ambient 改的正是这个形状。它把「× Pod 数」换成了「× 节点数」:ztunnel 每节点一个,waypoint 按命名空间或服务账户部署。这不是优化,是换了度量维度。

三、三种数据面形态

形态一:每 Pod 一个 sidecar

Istio sidecar 模式、Linkerd,以及几乎所有基于 Envoy 的网格。代理和应用容器共享 Pod 的网络命名空间,流量经 iptables 或 eBPF 重定向后先过代理。每个请求至少多两跳(客户端 sidecar → 服务端 sidecar)。

优点是 L7 能力完整:按 header 路由、流量切分、细粒度授权、JWT 校验。缺点就是上一节那个乘法。

形态二:每节点 L4 + 按需 L7 waypoint

Istio ambient 模式,以及用 eBPF 做 L4 的 Cilium。应用 Pod 里不再有代理,节点上跑一个 ztunnel(Rust 写的轻量代理)负责 mTLS、身份和 L4 策略;只有当你真的需要 L7 能力(流量转移、请求路由、丰富授权)时,才在命名空间或服务账户级别部署一个 waypoint 代理。

关键点:L4 是默认,L7 是按需。大部分服务间调用根本不需要 HTTP 层的路由规则,却被迫为此在每个 Pod 里塞一个完整的 Envoy。

形态三:云厂商托管

AWS App Mesh、Azure Service Fabric 之类,网格作为托管服务提供。理论上最省心------但 App Mesh 已经在 2026 年 9 月 30 日终止支持,官方建议迁移到 Amazon ECS Service Connect。这不是「某个小厂跑路」,是「云厂商自己承认:托管网格这条路线撑不住了」。托管路线正在收缩,这本身就是一条重要信号。

四、2026 年到底发生了什么

按时间顺序,这半年密集发生的事情构成了整张图景:

2024 年 11 月,Istio 1.24 把 ambient 推上 GA。 ztunnel、waypoints 和相关 API 被 Istio TOC 标记为 Stable。ambient 概念 2022 年 9 月提出,到 GA 用了 26 个月,Solo.io、Google、Microsoft、Intel、Aviatrix、Huawei、IBM、Red Hat 都参与了。同一篇公告里还有一个常被忽略的细节:当时 ztunnel 镜像在 Docker Hub 上的下载量已经超过 100 万次,仅公布前一周就有约 6.3 万次。同一版本还改了重试逻辑------此前重试只在客户端 sidecar 发生,1.24 起服务端 sidecar 也能检测「后端正在关闭连接、客户端却复用了这条连接」这类失败并自动重试,同时移除了默认重试 503 的策略(因为它对部分应用有副作用)。

2025 年 4 月 23 日,Kubernetes 1.33 让原生 sidecar 容器 GA。 这个特性从 2019 年 KEP-753 提案开始,v1.28 以 alpha 引入(2023 年 8 月),v1.29 转 beta 并默认开启,v1.33 稳定,feature gate 锁定在开启状态。

它的实现简单到有点反直觉:sidecar 就是一个 restartPolicy: Always 的 init 容器。

yaml 复制代码
initContainers:
  - name: log-shipper
    image: fluent/fluent-bit:3.1
    restartPolicy: Always          # ← 这一行把它从 init 容器变成原生 sidecar
    volumeMounts:
      - name: shared-logs
        mountPath: /var/log/app
        readOnly: true
    resources:
      requests: { cpu: 50m, memory: 64Mi }
      limits: { memory: 128Mi }
containers:
  - name: app
    image: my-app:latest

但它修掉的是实打实的老问题。启动顺序变成确定的 :sidecar 按声明顺序启动,每个都启动完成且 startupProbe 通过之后才启动下一个。停止顺序是逆的 :在最后一个主容器完全退出之后,sidecar 才收到 SIGTERM;声明在第一个的 sidecar 最后被停。Job 能正常结束了------旧模式下 Job 的判定条件是「所有容器都退出」,而日志代理是设计成永远不退的,于是批量任务和 AI/ML 数据处理任务会永远挂着。

它还支持 startup / readiness / liveness 探针:sidecar 的 readinessProbe 会计入 Pod 的 ready 状态,代理不健康时 Pod 不会进 Service 的 endpoints。资源上,sidecar 计入 Pod 的有效请求(Pod overhead 加上「应用与 sidecar 请求之和」和「最大常规 init 容器请求」两者取大)。

最值得警惕的坑:MutatingWebhook 会把 restartPolicy: Always 剥掉 。Istio 自己的注入 webhook 就是 MutatingWebhook。一旦字段被剥,sidecar 退化成一次性 init 容器,Pod 会卡在 Init:0/1 状态。排查这类故障时,记得对比「提交的 YAML」和「kubectl get pod -o yaml 的实际结果」,而不是只看前者。

2026 年,Istio 1.31 和 1.32 把网格推向了 AI 负载。 1.31 新增 istio-agentgateway-waypoint GatewayClass,可以把 agentgateway 部署成 waypoint 代理;同时MCP 的配置服务端点开始要求已验证的控制面身份 (标准的 sidecar、gateway、ztunnel 流量不受影响)。1.32(2026 年 11 月 9 日发布,Release Managers 是来自 Microsoft 的 Jackson Greer、来自 Tetrate 的 Jianpeng He、来自 Solo.io 的 Jack Kawell)则解决了混合网格最头疼的问题:istio-east-west 网关可以通过 15443 端口的 AUTO_PASSTHROUGH listener 同时服务 sidecar 的多网络流量 ,于是混部集群不必再为 sidecar 单独准备一个网关(需要开启 AMBIENT_ENABLE_MULTI_NETWORK)。这意味着从 sidecar 迁到 ambient 不再需要一次性切换,可以按命名空间灰度。

1.32 还带来两个和「谁来干活」直接相关的改动:DestinationRule 新增 backendUtilization 策略,基于后端上报的 ORCA 负载报告做利用率感知负载均衡,把请求少发给更忙的实例;异常点检测也拆细了,outlierDetectionHttpErrorCodes 指定哪些 HTTP 状态码算错误,failurePercentageThreshold 允许按失败率摘除主机。

五、裁决:你的集群该走哪条路

你的情况 建议 理由
服务数 < 50,无跨集群要求,无 mTLS 合规强制 别上网格 NetworkPolicy + 客户端超时重试 + OpenTelemetry 已经覆盖大部分需求;网格的运维成本远超收益
服务数 50+,有专职平台团队,需要按工作负载身份授权 ambient 起步 ztunnel 覆盖 L4 与 mTLS,需要 L7 时再上 waypoint
已在 sidecar 模式上,Pod 数多且内存吃紧 按命名空间灰度迁 ambient Istio 1.32 的 east-west gateway 已经打通混合网格,不用一次性切换
强合规要求,全链路 mTLS 强制 sidecar 或 ambient 都行 关键是要有工作负载身份,别用 IP 白名单凑
AI 推理 / Agent 负载为主 ambient + agentgateway waypoint Istio 1.31 起 waypoint 可以换 agentgateway,1.31 已开始强制校验 MCP 端点的控制面身份
关键路径要求极低延迟 不要把 mesh 放进关键路径 每跳多一次代理,收益(mTLS、可观测)值不值得这笔延迟要自己算

六、什么时候不该上网格

这是最容易被跳过、但最值钱的一节。

网格解决四个问题:工作负载的加密身份、按身份(而不是按 IP)授权、流量治理(重试/超时/切分)、以及每一跳的统一遥测。如果你这四项都不需要------或者只需要其中一两项,而且能用更便宜的手段解决------那网格对你就是纯成本。

几个具体的否决信号:

  • 服务数少。网格的复杂度不随服务数线性下降,CRD、控制面、升级规划都是固定成本摊在少数服务头上。
  • 没有专职平台团队。行业里流传的经验值是每 15 个服务开发配 1 个平台工程师,低于这个配比,交付与稳定性指标会在几个月内开始退化。网格的运维能力必须有人兜底,没有人的网格就是躺在集群里的第二套网络。
  • 只是想解决日志采集问题。日志采集用 DaemonSet 就够,sidecar 模式在这里纯属把简单问题复杂化。
  • 只是想解决「服务发现」问题。Kubernetes 的 Service + DNS 已经做完了,网格在这件事上不提供额外价值。

七、如果你已经在 sidecar 模式上

迁移不是重写,是三步:

  1. 先量账 。用 Sidecar 资源裁剪代理可见的 egress 范围,让每个 sidecar 只知道自己该访问的服务。Istio 1.31 还支持用 ~ 前缀做排除式配置,例如 */* 加上 ~ns1/*,避免为少量例外枚举长白名单。这一步往往就能砍掉相当可观的一部分路由表和内存。
  2. 先迁原生 sidecar 容器 。把日志代理、配置热加载这类辅助容器从 containers 挪到 initContainers 并加上 restartPolicy: Always,拿到确定的启动与停止顺序、让 Job 能正常结束。注意核对 webhook 有没有把字段剥掉。
  3. 再按命名空间灰度 ambient 。用 kubectl label namespace <name> istio.io/dataplane=ambient 之类的路径逐个命名空间切换,配合 Istio 1.32 的 east-west gateway,sidecar 和 ambient 可以在同一个集群里共存。

八、最后一句

sidecar 不会消失。消失的是「每个 Pod 必须有一个代理」这个默认前提。

Kubernetes 把 sidecar 变成了原语,Istio 把代理从 Pod 挪到了节点,AWS 把托管网格这条路收了尾------三件事方向一致:把代理的成本从「随业务副本数线性放大」挪到「随基础设施规模摊薄」。

对你的团队来说,真正要做的决策不是「用不用网格」,而是**「你的请求路径上要不要放一个代理,以及放几个」**。

参考资料

#mermaid-svg-dHDEirim33PRi3iy{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-dHDEirim33PRi3iy .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-dHDEirim33PRi3iy .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-dHDEirim33PRi3iy .error-icon{fill:#552222;}#mermaid-svg-dHDEirim33PRi3iy .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-dHDEirim33PRi3iy .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-dHDEirim33PRi3iy .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-dHDEirim33PRi3iy .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-dHDEirim33PRi3iy .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-dHDEirim33PRi3iy .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-dHDEirim33PRi3iy .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-dHDEirim33PRi3iy .marker{fill:#333333;stroke:#333333;}#mermaid-svg-dHDEirim33PRi3iy .marker.cross{stroke:#333333;}#mermaid-svg-dHDEirim33PRi3iy svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-dHDEirim33PRi3iy p{margin:0;}#mermaid-svg-dHDEirim33PRi3iy .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-dHDEirim33PRi3iy .cluster-label text{fill:#333;}#mermaid-svg-dHDEirim33PRi3iy .cluster-label span{color:#333;}#mermaid-svg-dHDEirim33PRi3iy .cluster-label span p{background-color:transparent;}#mermaid-svg-dHDEirim33PRi3iy .label text,#mermaid-svg-dHDEirim33PRi3iy span{fill:#333;color:#333;}#mermaid-svg-dHDEirim33PRi3iy .node rect,#mermaid-svg-dHDEirim33PRi3iy .node circle,#mermaid-svg-dHDEirim33PRi3iy .node ellipse,#mermaid-svg-dHDEirim33PRi3iy .node polygon,#mermaid-svg-dHDEirim33PRi3iy .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-dHDEirim33PRi3iy .rough-node .label text,#mermaid-svg-dHDEirim33PRi3iy .node .label text,#mermaid-svg-dHDEirim33PRi3iy .image-shape .label,#mermaid-svg-dHDEirim33PRi3iy .icon-shape .label{text-anchor:middle;}#mermaid-svg-dHDEirim33PRi3iy .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-dHDEirim33PRi3iy .rough-node .label,#mermaid-svg-dHDEirim33PRi3iy .node .label,#mermaid-svg-dHDEirim33PRi3iy .image-shape .label,#mermaid-svg-dHDEirim33PRi3iy .icon-shape .label{text-align:center;}#mermaid-svg-dHDEirim33PRi3iy .node.clickable{cursor:pointer;}#mermaid-svg-dHDEirim33PRi3iy .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-dHDEirim33PRi3iy .arrowheadPath{fill:#333333;}#mermaid-svg-dHDEirim33PRi3iy .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-dHDEirim33PRi3iy .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-dHDEirim33PRi3iy .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-dHDEirim33PRi3iy .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-dHDEirim33PRi3iy .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-dHDEirim33PRi3iy .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-dHDEirim33PRi3iy .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-dHDEirim33PRi3iy .cluster text{fill:#333;}#mermaid-svg-dHDEirim33PRi3iy .cluster span{color:#333;}#mermaid-svg-dHDEirim33PRi3iy div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-dHDEirim33PRi3iy .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-dHDEirim33PRi3iy rect.text{fill:none;stroke-width:0;}#mermaid-svg-dHDEirim33PRi3iy .icon-shape,#mermaid-svg-dHDEirim33PRi3iy .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-dHDEirim33PRi3iy .icon-shape p,#mermaid-svg-dHDEirim33PRi3iy .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-dHDEirim33PRi3iy .icon-shape .label rect,#mermaid-svg-dHDEirim33PRi3iy .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-dHDEirim33PRi3iy .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-dHDEirim33PRi3iy .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-dHDEirim33PRi3iy :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;}#mermaid-svg-dHDEirim33PRi3iy .hot>*{fill:#ffe4ec!important;stroke:#c2185b!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .hot span{fill:#ffe4ec!important;stroke:#c2185b!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .hot tspan{fill:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .warn>*{fill:#fff4e5!important;stroke:#ef6c00!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .warn span{fill:#fff4e5!important;stroke:#ef6c00!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .warn tspan{fill:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .note>*{fill:#e8f0fe!important;stroke:#1a73e8!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .note span{fill:#e8f0fe!important;stroke:#1a73e8!important;stroke-width:2px!important;color:#000!important;}#mermaid-svg-dHDEirim33PRi3iy .note tspan{fill:#000!important;} 形态三:云厂商托管
应用 Pod
云厂商数据面

App Mesh 2026-09-30 终止支持

迁移至 ECS Service Connect
应用 Pod
形态二:按节点共享代理
应用 Pod

Pod 内无代理
ztunnel

每节点一个

L4 mTLS + 加密身份
waypoint

按需部署

流量切分 / L7 授权
应用 Pod

Pod 内无代理
形态一:每 Pod 一个代理
应用容器

Pod A
Envoy sidecar

每个副本一份
Envoy sidecar

每个副本一份
应用容器

Pod B
成本模型

形态一 约等于 单代理开销 × Pod 副本数 × 服务数

形态二 约等于 单代理开销 × 节点数 + waypoint 数

相关推荐
Eyfcom1 小时前
〖物流低代码实战 01〗物流页面可视化搭建的底层架构:协议、引擎与产物的三重奏
低代码·架构·快递系统·物料体系·物流低代码实战
浪遏10 小时前
recruitment-cli:让 AI 接手求职招聘,从架构到一次发送超时
架构·typescript·node.js
小雉系统12 小时前
BcoreOS安全通信架构:FsSession 抗算法后门安全设计
算法·安全·架构
JAVA前线13 小时前
用《实践论》分析前沿部署工程师:AI时代听见炮声的人
架构·ai编程
深入云栈17 小时前
Netty 4.2.x 源码深度解析 (二十三):ByteBuf 核心设计 —— 索引、类型与零拷贝
java·后端·架构
JackJiang17 小时前
IM踩坑:聊天消息ID怎么设计?一个UUID搞不定,我用双ID解决
后端·架构
聪明的笨猪猪17 小时前
企业知识库AI架构选型:落地导向的架构决策与组件清单
经验分享·面试·架构·embedding·数据库架构
Dawson Zhu18 小时前
Queen Planner深度解析:Agent竞争从模型时代进入系统时代
人工智能·语言模型·架构·aigc·agi
孟健19 小时前
我用 REA 逆向自己的 Electron 桌面端,扒出 178 个 IPC 通道后我反而放心了
架构·开源·ai编程