3. Cilium 组件架构:Agent、Operator、CNI 插件、Hubble Relay 的核心职责与版本依赖关系

Cilium 采用微服务化的控制面与数据面分离架构,核心组件包括 Cilium Agent、Cilium Operator、Cilium-CNI 插件 以及可选的 Hubble Relay。在准入控制校验版本漂移时,必须理解每个组件的职责边界及其版本耦合规则,否则极易出现组件间协议不兼容或功能降级。

3.1 组件核心职责对比

组件名称 部署形态 核心职责 关键数据面/控制面接口
Cilium Agent DaemonSet(每节点一个) 管理 eBPF 程序加载、端点(Endpoint)生命周期、网络策略执行、服务负载均衡、监控指标暴露 与 kube-apiserver 通信获取 Endpoint/Service/Policy;通过 Unix Socket 与 Cilium-CNI 交互
Cilium Operator Deployment(通常 1~2 副本) 集群级协调:IPAM(IP 地址管理)、CiliumNetworkPolicy 状态同步、节点间隧道/路由配置、CRD 状态清理 仅控制面操作,不参与数据面转发;依赖 kube-apiserver 和 etcd
Cilium-CNI 插件 二进制文件(位于 /opt/cni/bin/) 接收 kubelet CNI 调用,将 Pod 网络命名空间加入 Cilium 管理;调用 Agent 的 gRPC 接口完成端点创建 通过本地 Unix Socket 与同节点 Agent 通信;不直接访问 kube-apiserver
Hubble Relay Deployment(可选组件) 聚合集群内所有 Hubble 观测数据,提供全局 API 和 CLI 查询能力;支持多集群联邦 gRPC 连接各节点 Hubble 服务;依赖 Cilium Agent 暴露的观测数据
版本漂移校验要点: Agent 与 CNI 插件必须使用完全相同的版本(二进制同时发布),因为两者通过内部 protobuf 协议通信,字段变更会导致端点创建失败。Operator 和 Hubble Relay 允许小版本差异,但大版本必须对齐 Agent 的 API 版本。

3.2 组件间通信与版本依赖关系

下图展示了四个组件之间的通信链路及版本耦合边界。箭头方向表示调用或数据流方向,标注了协议类型和版本约束等级。

Cilium 组件架构与版本依赖关系图 Cilium 组件架构与版本依赖关系 Cilium Agent DaemonSet · 每节点一个 Cilium Operator Deployment · 集群级协调 Cilium-CNI 插件 二进制 · 被 kubelet 调用 Hubble Relay Deployment · 观测聚合 Unix Socket · 版本必须完全一致 kube-apiserver · 大版本对齐 gRPC · 小版本兼容 CNI ADD/DEL 版本依赖规则总结 1. Agent ↔ CNI 插件:版本必须完全一致(同一发布包) 2. Agent ↔ Operator:大版本必须对齐(如 v1.14.x 与 v1.14.y 兼容) 3. Agent ↔ Hubble Relay:小版本兼容(v1.14.1 ↔ v1.14.5 可通信) 4. 所有组件与 kube-apiserver:依赖 Kubernetes API 版本,与 Cilium 版本解耦 5. 升级时必须先升级 Agent/CNI,再升级 Operator,最后升级 Hubble Relay

3.3 版本漂移典型场景与影响

在准入控制校验中,以下三种版本漂移场景需要重点拦截:

  • Agent 与 CNI 插件版本不一致: 最常见且破坏性最大。CNI 插件调用 Agent 的 gRPC 接口创建端点时,若 protobuf 消息结构不匹配,会导致 Pod 创建失败,kubelet 反复重试直至超时。
  • Operator 版本高于 Agent: Operator 可能下发 Agent 不支持的 CRD 字段或 IPAM 策略,导致 Agent 日志报错、策略无法生效。
  • Hubble Relay 版本低于 Agent: Relay 无法解析 Agent 上报的新观测字段,导致 Hubble UI/CLI 查询结果缺失或解析异常。
准入校验策略建议: 在 Helm 升级或 Operator 部署准入 Webhook 中,强制校验 Agent 与 CNI 插件的镜像 tag 完全一致;对 Operator 和 Hubble Relay 使用 semver 比较,拒绝大版本不匹配的变更请求。

3.4 组件版本矩阵示例

以下表格展示了 Cilium v1.14.x 系列中各组件的版本兼容关系,供准入控制规则编写参考:

Cilium 版本 Agent 版本 CNI 插件版本 Operator 版本 Hubble Relay 版本 兼容性
v1.14.0 v1.14.0 v1.14.0 v1.14.0 v1.14.0 ✅ 完全兼容
v1.14.1 v1.14.1 v1.14.0 v1.14.1 v1.14.1 ❌ Agent/CNI 不匹配
v1.14.2 v1.14.2 v1.14.2 v1.14.0 v1.14.2 ⚠️ Operator 降级,功能受限
v1.14.3 v1.14.3 v1.14.3 v1.14.3 v1.14.0 ⚠️ Relay 无法解析新字段

3.5 版本校验的代码级实现参考

在准入控制 Webhook 中,可以通过解析容器镜像 tag 或读取 Cilium Agent 的版本端点来实现校验。以下是一个简化版的 Go 伪代码片段:

// 伪代码:准入控制版本校验逻辑
func validateCiliumVersions(pod corev1.Pod) error {
    agentVersion := getImageTag(pod, "cilium-agent")
    cniVersion   := getImageTag(pod, "cilium-cni")
    operatorVersion := getImageTag(pod, "cilium-operator")
    relayVersion := getImageTag(pod, "hubble-relay")

    // 规则1:Agent 与 CNI 必须完全一致
    if agentVersion != cniVersion {
        return fmt.Errorf("Agent version %s != CNI version %s", agentVersion, cniVersion)
    }

    // 规则2:Operator 大版本必须与 Agent 一致
    if semver.Major(agentVersion) != semver.Major(operatorVersion) {
        return fmt.Errorf("Agent major %d != Operator major %d",
            semver.Major(agentVersion), semver.Major(operatorVersion))
    }

    // 规则3:Relay 版本不能低于 Agent 版本
    if semver.Compare(relayVersion, agentVersion) < 0 {
        return fmt.Errorf("Relay version %s < Agent version %s", relayVersion, agentVersion)
    }

    return nil
}
注意: 上述代码仅为示例,生产环境中还需考虑 pre-release 标签(如 rc1、alpha)的比较逻辑,以及未部署 Hubble Relay 时的跳过处理。建议使用 blang/semver 或 Masterminds/semver 库进行语义化版本比较。