You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何为K8s集群中Node X上的所有Pod配置Cilium出口网关策略?

按节点筛选Pod的Cilium Egress策略实现方案

一、直接按spec.nodeName筛选的局限

Cilium Egress Gateway Policy的podSelector仅支持匹配Pod的标签,不直接支持基于spec.nodeName的字段选择,因此需要通过给Pod动态添加节点名称标签的方式实现按节点筛选的需求。

二、DaemonSet实现动态添加Pod节点标签

1. 核心逻辑

在每个节点上运行一个DaemonSet Pod,负责:

  • 监听当前节点上的所有Pod(含新创建的)
  • 检查Pod是否带有节点名称标签(例如node-name: <节点名>)
  • 若未携带该标签,调用K8s API为Pod添加标签

2. 完整DaemonSet配置示例

apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: pod-node-labeler
  namespace: kube-system
  labels:
    k8s-app: pod-node-labeler
spec:
  selector:
    matchLabels:
      k8s-app: pod-node-labeler
  template:
    metadata:
      labels:
        k8s-app: pod-node-labeler
    spec:
      serviceAccountName: pod-node-labeler-sa
      containers:
      - name: labeler
        image: bitnami/kubectl:latest
        command:
        - /bin/sh
        - -c
        - |
          NODE_NAME=$(NODE_NAME)
          echo "Running on node: $NODE_NAME"
          # 循环监听节点Pod,每秒执行一次检查
          while true; do
            # 获取当前节点上未携带node-name标签的Pod
            PODS=$(kubectl get pods --all-namespaces -o jsonpath='{range .items[?(@.spec.nodeName == "'$NODE_NAME'" && !has(.metadata.labels.node-name))]}{.metadata.namespace}/{.metadata.name}{"\n"}')
            if [ -n "$PODS" ]; then
              echo "Labeling target pods:"
              echo "$PODS"
              while IFS=/ read -r NS POD; do
                kubectl label pod -n "$NS" "$POD" node-name="$NODE_NAME" --overwrite=false
              done <<< "$PODS"
            fi
            sleep 1
          done
      tolerations:
      - key: node-role.kubernetes.io/master
        effect: NoSchedule  # 允许在Master节点运行(按需启用)

3. 配套ServiceAccount与RBAC配置

为DaemonSet Pod赋予修改Pod标签的最小权限:

apiVersion: v1
kind: ServiceAccount
metadata:
  name: pod-node-labeler-sa
  namespace: kube-system

---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: pod-node-labeler-role
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["get", "list", "update", "patch"]

---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: pod-node-labeler-binding
subjects:
- kind: ServiceAccount
  name: pod-node-labeler-sa
  namespace: kube-system
roleRef:
  kind: ClusterRole
  name: pod-node-labeler-role
  apiGroup: rbac.authorization.k8s.io

4. 部署步骤

  1. 先创建ServiceAccount、ClusterRole和ClusterRoleBinding
  2. 再部署DaemonSet
  3. 可替换镜像为自定义开发的程序镜像(用Go/Python编写),提升长期运行稳定性

三、节点上API Server凭证的安全性说明

K8s会自动为每个Pod挂载ServiceAccount凭证(路径/var/run/secrets/kubernetes.io/serviceaccount/),该机制是安全的,理由如下:

  • 凭证为临时有效期,会自动轮换,不会长期有效
  • 凭证仅关联当前ServiceAccount的权限,我们配置的ClusterRole仅允许修改Pod标签,实现了权限最小化
  • 凭证仅能在Pod内部访问,节点上的其他进程无Pod权限则无法读取
  • 若需进一步降低风险,可缩小ClusterRole的权限范围,例如仅允许修改指定命名空间的Pod,或仅允许添加特定标签

四、Cilium Egress Gateway Policy配置示例

完成标签自动添加后,即可通过podSelector匹配节点标签:

apiVersion: cilium.io/v2
kind: CiliumEgressGatewayPolicy
metadata:
  name: egress-node-x
spec:
  selector:
    matchLabels:
      node-name: node-x  # 匹配调度到node-x的所有Pod
  egressGateway:
    nodeSelector:
      matchLabels:
        kubernetes.io/hostname: node-x  # 指定出口网关节点
  destinationCIDRs:
  - 0.0.0.0/0  # 根据实际业务需求调整目标CIDR

内容的提问来源于stack exchange,提问作者Vishesh Agarwal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.08 14:50:30