3. Envoy 数据面架构:线程模型、连接池与核心资源
Envoy 作为高性能数据面代理,其架构设计直接决定了数据包处理路径的效率和资源消耗。理解 Envoy 的线程模型、连接池机制以及 Listener/Cluster/Endpoint 三大核心概念,是分析 CNI 缓存命中瓶颈的前提。Envoy 采用单进程多线程架构,通过事件驱动和异步非阻塞 I/O 实现高吞吐与低延迟。
3.1 Envoy 线程模型:主线程与 Worker 线程
Envoy 的线程模型分为三类角色:主线程(Main Thread)、Worker 线程 和 文件刷新线程(File Flush Thread)。主线程负责配置加载、证书轮换、统计刷新等控制面任务;Worker 线程负责处理所有网络 I/O 和连接事件;文件刷新线程仅负责异步写入访问日志。
下图展示了 Envoy 的线程模型与数据流关系:
3.2 连接池:连接复用与缓存
Envoy 的连接池是数据面性能的核心组件。每个 Worker 线程为每个上游集群维护独立的连接池,连接池按 协议类型(HTTP/1.1、HTTP/2、TCP)和 上游端点 进行分桶。连接池的核心目标是减少连接建立开销,提高连接复用率。
| 连接池类型 | 复用策略 | 最大连接数 | 空闲超时 | 适用场景 |
|---|---|---|---|---|
| HTTP/1.1 连接池 | 请求级复用(Keep-Alive) | 可配置(默认 1024) | 可配置(默认 1h) | 传统 HTTP 服务 |
| HTTP/2 连接池 | 多路复用(流级) | 通常 1 条连接 | 可配置 | gRPC / 微服务 |
| TCP 连接池 | 无复用(透传) | 无限制 | 无 | 原始 TCP 代理 |
3.3 Listener / Cluster / Endpoint 核心概念
Envoy 的配置模型围绕三个核心资源构建:Listener(监听器)、Cluster(集群)和 Endpoint(端点)。这三者构成了数据面转发的完整链路。
3.3.1 Listener(监听器)
Listener 定义了 Envoy 如何接收入站流量。每个 Listener 绑定一个 IP:Port,并关联一组过滤器链(Filter Chain)来处理协议解析和路由决策。Listener 可以配置多个地址,支持透明代理和端口复用。
listeners:
- name: ingress_listener
address:
socket_address:
address: 0.0.0.0
port_value: 80
filter_chains:
- filters:
- name: envoy.filters.network.http_connection_manager
typed_config:
"@type": type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager
stat_prefix: ingress_http
route_config:
name: local_route
virtual_hosts:
- name: backend
domains: ["*"]
routes:
- match:
prefix: "/"
route:
cluster: backend_cluster
3.3.2 Cluster(集群)
Cluster 定义了 Envoy 如何将流量转发到一组上游服务。每个 Cluster 包含连接池配置、负载均衡策略、健康检查规则以及服务发现类型(静态、DNS、EDS 等)。Cluster 是连接池的归属单位。
| Cluster 属性 | 说明 | 典型值 |
|---|---|---|
| type | 服务发现方式 | STATIC / STRICT_DNS / EDS / LOGICAL_DNS |
| connect_timeout | 连接超时 | 0.25s |
| per_connection_buffer_limit_bytes | 连接缓冲区大小 | 32768 (32KB) |
| lb_policy | 负载均衡策略 | ROUND_ROBIN / LEAST_REQUEST / RING_HASH / MAGLEV |
| circuit_breakers | 熔断配置 | max_connections / max_pending_requests / max_requests |
3.3.3 Endpoint(端点)
Endpoint 是 Cluster 下的具体上游实例,通常对应一个 Pod 的 IP:Port。Endpoint 由服务发现机制动态更新,Envoy 通过 EDS(Endpoint Discovery Service)从控制面获取最新的端点列表。每个 Endpoint 可以携带健康状态、权重、区域等元数据。
clusters:
- name: backend_cluster
type: EDS
eds_cluster_config:
eds_config:
path: /etc/envoy/eds.conf
lb_policy: LEAST_REQUEST
connect_timeout: 0.25s
circuit_breakers:
thresholds:
- priority: DEFAULT
max_connections: 1000
max_requests: 2000
下图展示了 Listener → Cluster → Endpoint 的完整转发链路:
3.4 核心概念与 CNI 缓存的协同关系
在 Kubernetes 环境中,Envoy 的 Listener/Cluster/Endpoint 与 CNI 缓存存在以下协同关系:
- Endpoint 变更触发 CNI 缓存失效: 当 Pod 扩缩容或迁移时,Endpoint 列表发生变化,Envoy 通过 EDS 获取更新。此时,Worker 线程的连接池中指向旧 Endpoint 的连接需要被销毁,新连接需要重新建立。CNI 缓存中的路由条目也可能因 Pod IP 变化而失效。
- 连接池复用降低 CNI 缓存查找频率: 高连接复用率意味着每个连接可以处理多个请求,从而减少每次请求的 CNI 缓存查找次数。连接池的命中率越高,CNI 缓存的压力越小。
- Worker 线程隔离影响缓存局部性: 每个 Worker 线程拥有独立的连接池,这意味着 CNI 缓存条目可能被多个 Worker 线程重复缓存。如果 Worker 线程数过多,CNI 缓存的重复条目会增加内存开销,但可以减少跨线程竞争。