4. Cilium 网络策略基础:Identity 概念、Endpoint 分组、L3/L4 网络策略 YAML 编写

在蓝绿发布场景中,精准控制流量是保障业务连续性的核心。Cilium 基于 eBPF 实现的网络策略,摒弃了传统基于 IP 和端口的静态模型,引入了 Identity(身份) 和 Endpoint(端点) 的抽象层。本章将深入剖析这两个核心概念,并手把手编写 L3/L4 层网络策略 YAML。

4.1 Identity 概念:Cilium 的“数字指纹”

传统 Kubernetes NetworkPolicy 依赖 Pod 的 IP 地址或标签选择器,但在动态编排环境中,Pod IP 频繁变化,导致策略维护成本极高。Cilium 的 Identity 机制解决了这一痛点。

  • 定义:Identity 是一个 64 位无符号整数,由 Cilium Agent 根据 Pod 的标签集合(Labels)计算得出。具有相同标签集合的 Pod 共享同一个 Identity。
  • 生命周期:Identity 在 Pod 创建时分配,在 Pod 删除时回收。Cilium 通过 KV Store(如 etcd)在集群范围内同步 Identity 与标签的映射关系。
  • 优势:策略规则不再绑定易变的 IP,而是绑定稳定的 Identity。即使 Pod 被调度到不同节点,只要标签不变,策略依然生效。
关键理解:Identity 是 Cilium 实现“语义化”网络策略的基石。它让策略从“允许 IP 10.0.0.1 访问 10.0.0.2”进化为“允许所有带有 app=frontend 标签的 Pod 访问带有 app=backend 标签的 Pod”。
Cilium Identity 与 Endpoint 关系 Cilium Identity 与 Endpoint 映射关系 Pod A labels: app=web IP: 10.0.1.5 Pod B labels: app=web IP: 10.0.2.8 Identity: 12345 标签集合: app=web version=v1 env=prod Endpoint ID: 6789 Identity: 12345 Pod A: 10.0.1.5 Pod B: 10.0.2.8 (共享同一 Identity) 说明:相同标签的 Pod 共享同一 Identity,Cilium 策略基于 Identity 而非 IP 进行匹配。

4.2 Endpoint 分组:从 Pod 到策略目标的映射

Endpoint 是 Cilium 对网络可达实体的抽象。一个 Endpoint 可以是一个 Pod、一个外部服务,甚至是一个主机。Cilium Agent 会为每个 Endpoint 维护一个本地状态机,记录其 Identity、IP 地址、安全策略等信息。

概念 粒度 生命周期 策略匹配方式
Identity 标签集合 全局,跨节点 基于标签哈希
Endpoint 单个 Pod/实体 本地,节点级 基于 Identity 引用
K8s Pod 单个容器组 由 K8s 管理 通过标签选择器

在编写网络策略时,我们通过 Endpoint Selector 来定义策略的目标。Cilium 支持两种选择器:

  • matchLabels:精确匹配标签键值对。
  • matchExpressions:支持 In、NotIn、Exists、DoesNotExist 等表达式。
蓝绿发布场景应用:在蓝绿发布中,我们可以为“蓝”版本和“绿”版本分别打上不同的标签(如 version=blue 和 version=green)。通过 Endpoint Selector,策略可以精确控制流量只流向特定版本,实现灰度验证。

4.3 L3/L4 网络策略 YAML 编写

Cilium 网络策略使用 CiliumNetworkPolicy CRD 定义。L3 层控制基于 IP 或 CIDR 的访问,L4 层控制基于端口和协议的访问。下面通过一个完整的示例演示如何编写策略。

4.3.1 基础策略结构

apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
  name: allow-frontend-to-backend
  namespace: production
spec:
  endpointSelector:
    matchLabels:
      app: backend
  ingress:
  - fromEndpoints:
    - matchLabels:
        app: frontend
    toPorts:
    - ports:
      - port: "8080"
        protocol: TCP

策略解读:

  • endpointSelector:策略应用于 app=backend 的 Pod。
  • fromEndpoints:只允许来自 app=frontend 的 Pod 的入站流量。
  • toPorts:仅允许访问 TCP 8080 端口。

4.3.2 L3 层策略:基于 CIDR 的访问控制

当需要允许外部 IP 范围访问时,使用 fromCIDR 或 toCIDR。

apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
  name: allow-external-monitoring
  namespace: production
spec:
  endpointSelector:
    matchLabels:
      app: backend
  ingress:
  - fromCIDR:
    - 10.0.0.0/24
    - 192.168.1.0/24
    toPorts:
    - ports:
      - port: "9090"
        protocol: TCP
注意:使用 fromCIDR 时,Cilium 会为每个 CIDR 段创建一个特殊的 Identity。如果 CIDR 范围过大,可能导致 Identity 数量膨胀,影响性能。建议尽量使用 fromEndpoints 基于标签的策略。

4.3.3 L4 层策略:精细端口控制

L4 策略可以结合 toPorts 和 rules 实现更精细的控制,例如限制 HTTP 方法或 TLS 证书。

apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
  name: allow-http-get-only
  namespace: production
spec:
  endpointSelector:
    matchLabels:
      app: backend
  ingress:
  - fromEndpoints:
    - matchLabels:
        app: frontend
    toPorts:
    - ports:
      - port: "80"
        protocol: TCP
      rules:
        http:
        - method: "GET"
          path: "/api/v1/.*"
L3/L4 策略执行流程 Cilium L3/L4 网络策略执行流程 源 Pod app=frontend L3 检查 Identity 匹配 CIDR 匹配 L4 检查 端口匹配 协议匹配 目标 Pod app=backend 拒绝 (DROP) 说明:流量依次经过 L3 和 L4 检查,任意一层不通过则直接 DROP,通过后到达目标 Pod。

4.4 策略生效验证与调试

编写完策略后,建议通过以下步骤验证:

  1. 应用策略:kubectl apply -f policy.yaml
  2. 查看策略状态:kubectl get ciliumnetworkpolicies -n production
  3. 检查 Endpoint 状态:kubectl exec -n kube-system cilium-xxxxx -- cilium endpoint list
  4. 流量测试:使用 curl 或 kubectl exec 发起测试请求,观察是否被允许或拒绝。
  5. 监控日志:通过 cilium monitor 命令实时查看策略命中情况。
调试技巧:如果策略未生效,首先检查 Endpoint 的 Identity 是否正确。使用 cilium endpoint get <endpoint-id> 查看其标签和 Identity 映射。常见问题包括标签拼写错误或 Namespace 不匹配。

4.5 本章小结