乐于分享
好东西不私藏

K8s 网络插件大全:CNI 原理、Flannel/Calico/Cilium 深度解析与故障排查

K8s 网络插件大全:CNI 原理、Flannel/Calico/Cilium 深度解析与故障排查

 

KUBERNETES NETWORKING

 

K8s 网络插件大全

 

   CNI 原理 · Flannel · Calico · Cilium · Weave · 云原生插件
   从概念到实战,从安装到故障排查,一文吃透 K8s 网络
 

 

   CNI 标准
   Overlay 网络
   BGP 路由
   eBPF 内核
 

一、K8s 网络模型基础

🎯 K8s 网络三大基本原则(必须满足)
1. 每个 Pod 有唯一 IP,无需 NAT 即可与集群内所有 Pod 通信
2. Node 上的 Agent 可以直接与节点上所有 Pod 通信
3. Pod 视角下的本机 IP = 外部看到的 IP(无 IP 伪装)
K8s 网络通信层次:

  ┌──────────────────────────────────────────────────────────┐
  │  同 Pod 内容器                                            │
  │  Container A ←──── lo (127.0.0.1) ────→ Container B     │
  └──────────────────────────────────────────────────────────┘
                          │ veth pair
  ┌──────────────────────────────────────────────────────────┐
  │  同节点 Pod 间                                            │
  │  Pod A (10.244.0.2) ←──── cbr0/bridge ────→ Pod B       │
  └──────────────────────────────────────────────────────────┘
                          │ 物理网卡/隧道/路由
  ┌──────────────────────────────────────────────────────────┐
  │  跨节点 Pod 间                                            │
  │  Node1 Pod ←──── CNI 插件负责 ────→ Node2 Pod           │
  └──────────────────────────────────────────────────────────┘
                          │ kube-proxy / eBPF
  ┌──────────────────────────────────────────────────────────┐
  │  Pod ↔ Service                                           │
  │  ClusterIP / NodePort / LoadBalancer / ExternalName      │
  └──────────────────────────────────────────────────────────┘

二、CNI 是什么?插件标准详解

CNI(Container Network Interface) 是 CNCF 制定的容器网络接口标准,定义了容器运行时(如 kubelet)如何调用网络插件,以及插件如何为容器配置网络。

📦 CNI 插件的三大职责
  1. 为每个 Pod 分配唯一 IP(IPAM)
  2. 在 Pod 网卡和节点网络之间建立连通性(路由/隧道)
  3. Pod 删除时清理网络配置
BASH

# CNI 插件调用流程(kubelet 视角)

# 1. Pod 创建:kubelet 调用 CRI(containerd),CRI 调用 CNI

# 配置文件位置:

ls /etc/cni/net.d/

# 10-calico.conflist   或   10-flannel.conflist

# 插件二进制位置:

ls /opt/cni/bin/

# calico  calico-ipam  flannel  host-local  bridge  loopback …

# 2. CNI 调用链(以 Calico 为例)

# kubelet → /etc/cni/net.d/10-calico.conflist → /opt/cni/bin/calico

# CNI 需实现两个接口:

#   ADD  → 为容器配置网络(分配 IP、建立路由)

#   DEL  → 清理容器网络(释放 IP、删除路由)

CNI 插件类型 代表产品 原理 特点
Overlay 叠加网络 Flannel VXLAN
Weave
隧道封装,二层模拟 简单通用,有封装开销
Underlay 路由网络 Calico BGP
Flannel host-gw
直接路由,无封装 高性能,依赖底层网络
eBPF 内核加速 Cilium eBPF bypass iptables 极高性能,可观测性强
IPVLAN/MACVLAN Multus + 子插件 直接共享宿主网卡 超低延迟,适合 SR-IOV

三、Flannel:最易上手的 Overlay 网络

3.1 架构与原理

Flannel VXLAN 数据流:

Node1 (10.244.0.0/24)           Node2 (10.244.1.0/24)
┌──────────────────────┐         ┌──────────────────────┐
│  Pod-A (10.244.0.2)  │         │  Pod-B (10.244.1.3)  │
│   eth0 ──► veth      │         │   eth0 ──► veth      │
│           │          │         │           │          │
│         cni0         │         │         cni0         │
│    (bridge 网桥)       │         │    (bridge 网桥)       │
│           │          │         │           │          │
│         flannel.1    │─VXLAN──►│         flannel.1    │
│   (VTEP 封装设备)      │UDP:8472 │   (VTEP 解封装设备)    │
│           │          │         │           │          │
│          eth0         │─────────│          eth0         │
│    (物理网卡 192.168.x) │         │    (物理网卡 192.168.y) │
└──────────────────────┘         └──────────────────────┘

数据流:Pod-A → veth → cni0 → flannel.1(VXLAN封装) → eth0 → 物理网络
       → eth0(Node2) → flannel.1(解封装) → cni0 → veth → Pod-B
BASH

# Flannel 安装(适用于 K8s 1.28+)

kubectl apply -f https://github.com/flannel-io/flannel/releases/latest/download/kube-flannel.yml

# 关键配置文件

cat /etc/cni/net.d/10-flannel.conflist

# {

#   “name”: “cbr0”,

#   “cniVersion”: “0.3.1”,

#   “plugins”: [

#     {

#       “type”: “flannel”,

#       “delegate”: {

#         “hairpinMode”: true,

#         “isDefaultGateway”: true

#       }

#     },

#     { “type”: “portmap”, “capabilities”: { “portMappings”: true } }

#   ]

# }

# 查看 Flannel 子网分配

cat /run/flannel/subnet.env

# FLANNEL_NETWORK=10.244.0.0/16

# FLANNEL_SUBNET=10.244.0.1/24

# FLANNEL_MTU=1450

# FLANNEL_IPMASQ=true

3.2 Flannel 三种后端模式

Backend 原理 性能 要求
vxlan(默认) UDP 封装二层帧,VTEP 设备 中等(有封装开销) 无特殊要求,最通用
host-gw 直接添加静态路由,无封装 最高(接近裸机) 所有节点必须在同一子网
wireguard 加密隧道(WireGuard) 中等(加密开销) 内核 5.6+ / WireGuard 模块
BASH

# 切换 backend 为 host-gw(高性能,需同子网)

kubectl edit cm -n kube-flannel kube-flannel-cfg

# 修改:

# “Backend”: {

#   “Type”: “host-gw”

# }

kubectl rollout restart daemonset -n kube-flannel kube-flannel-ds

# 验证:节点路由表中能看到其他节点的 Pod CIDR 路由

ip route | grep flannel

# 10.244.1.0/24 via 192.168.1.102 dev eth0

# 10.244.2.0/24 via 192.168.1.103 dev eth0

四、Calico:企业级高性能 BGP 网络

4.1 架构与原理

🦅 Calico 核心优势
• 纯三层路由,无隧道封装,性能最优
• 支持 BGP / BGP-RR / IPIP / VXLAN 多种模式
• 内置 NetworkPolicy 功能,支持 L3/L4 防火墙
• 支持 GlobalNetworkPolicy、HostEndpoint 等企业级安全特性
Calico 组件架构:

  ┌─────────────────────────────────────────────────────┐
  │  Control Plane                                       │
  │  ┌─────────────┐   ┌─────────────┐                  │
  │  │  calico-kube │   │  Typha      │                  │
  │  │  -controllers│   │ (scale代理) │                  │
  │  └─────────────┘   └─────────────┘                  │
  └──────────────────────────┬──────────────────────────┘
                             │ watch K8s API
  ┌──────────────────────────▼──────────────────────────┐
  │  每个 Node 上的 DaemonSet                             │
  │  ┌──────────────────────────────────────────────┐   │
  │  │  Felix (核心代理)                              │   │
  │  │  • 路由同步、iptables规则、IP分配通知            │   │
  │  └──────────────────────────────────────────────┘   │
  │  ┌──────────────────────────────────────────────┐   │
  │  │  BIRD (BGP 路由协议守护进程)                   │   │
  │  │  • 与其他节点交换 BGP 路由                     │   │
  │  └──────────────────────────────────────────────┘   │
  │  ┌──────────────────────────────────────────────┐   │
  │  │  calico-ipam (IP 地址管理)                    │   │
  │  └──────────────────────────────────────────────┘   │
  └─────────────────────────────────────────────────────┘
BASH

# Calico 安装(Operator 方式,推荐)

kubectl create -f https://raw.githubusercontent.com/projectcalico/calico/v3.28.0/manifests/tigera-operator.yaml

kubectl create -f https://raw.githubusercontent.com/projectcalico/calico/v3.28.0/manifests/custom-resources.yaml

# 查看安装状态

kubectl get tigerastatus

# NAME        AVAILABLE   PROGRESSING   DEGRADED   SINCE

# apiserver   True        False         False      10m

# calico      True        False         False      10m

# 或直接 manifest 方式

kubectl apply -f https://raw.githubusercontent.com/projectcalico/calico/v3.28.0/manifests/calico.yaml

4.2 Calico 模式配置

YAML

# 查看当前模式

kubectl get felixconfiguration default -o yaml | grep -E ‘encapsulation|routeMode’

# — 方式 1:纯 BGP(最高性能,需三层互通)—

cat <<EOF | kubectl apply -f –

apiVersion: operator.tigera.io/v1

kind: Installation

metadata:

 name: default

spec:

 calicoNetwork:

   bgp: Enabled

   ipPools:

   – cidr: 10.244.0.0/16

     encapsulation: None

     natOutgoing: Enabled

EOF

# — 方式 2:IPIP(兼容性最好,有轻微开销)—

# encapsulation: IPIP

# — 方式 3:VXLAN(不需要 BGP,适合云环境)—

# encapsulation: VXLAN

# bgp: Disabled

# 验证路由(纯 BGP 模式下节点路由直达)

ip route | grep bird

# 10.244.1.0/26 via 192.168.1.102 dev eth0 proto bird

# 10.244.2.0/26 via 192.168.1.103 dev eth0 proto bird

4.3 Calico NetworkPolicy

YAML

# 示例:仅允许 frontend 访问 backend 的 8080 端口

apiVersion: projectcalico.org/v3

kind: NetworkPolicy

metadata:

 name: allow-frontend-to-backend

 namespace: production

spec:

 selector: app == ‘backend’

 ingress:

 – action: Allow

   protocol: TCP

   source:

     selector: app == ‘frontend’

   destination:

     ports:

     – 8080

 – action: Deny   # 默认拒绝其他所有入站

# GlobalNetworkPolicy:全局策略(跨 namespace)

apiVersion: projectcalico.org/v3

kind: GlobalNetworkPolicy

metadata:

 name: block-external-ssh

spec:

 selector: all()

 ingress:

 – action: Deny

   protocol: TCP

   destination:

     ports:

     – 22

   source:

     notNets:

     – 192.168.0.0/16  # 允许内网,拒绝外部

五、Cilium:eBPF 驱动的下一代网络

🚀 Cilium 为什么是未来?
eBPF 内核级别:完全绕过 iptables,性能提升 300%+
L7 策略:支持 HTTP/gRPC/Kafka 等应用层协议的访问控制
Hubble 可观测性:内置流量监控、拓扑图、Prometheus 集成
Service Mesh 替代:无需 Sidecar,eBPF 内核实现 mTLS

5.1 eBPF 原理

传统 iptables 路径 vs eBPF 路径:

传统(kube-proxy + iptables):
  包到达 → netfilter hook → iptables 规则链(可能上千条)→ 内核协议栈 → 目标

eBPF(Cilium):
  包到达 → eBPF hook(XDP/TC)→ eBPF 程序直接转发 → 目标
  
  优势:
  ✓ 无 iptables 规则,规则数不影响性能
  ✓ 支持 O(1) 连接查找(BPF map)
  ✓ 可在内核态实现 L7 协议解析
  ✓ 延迟降低 30-50%,吞吐提升 20-40%
BASH

# Cilium 安装(Helm 方式,推荐)

helm repo add cilium https://helm.cilium.io/

helm repo update

# 基础安装(替换 kube-proxy)

helm install cilium cilium/cilium –version 1.15.0 \

 –namespace kube-system \

 –set kubeProxyReplacement=true \

 –set k8sServiceHost=<API_SERVER_IP> \

 –set k8sServicePort=6443 \

 –set hubble.relay.enabled=true \

 –set hubble.ui.enabled=true

# 验证安装

cilium status

# KVStore:                 Ok   Disabled

# Kubernetes:              Ok   1.29+ (v1.29.0)

# Kubernetes APIs:         Ok   cilium/v2::CiliumNetworkPolicy

# KubeProxyReplacement:    True   NodePort (SNAT, 30000-32767)

# Host Routing:            Legacy (No BPF NodePort)

# Cilium:                  Ok   10 healthy (10 desired)

5.2 Hubble 流量可观测

BASH

# 安装 Hubble CLI

HUBBLE_VERSION=$(curl -s https://raw.githubusercontent.com/cilium/hubble/master/stable.txt)

curl -L –remote-name-all https://github.com/cilium/hubble/releases/download/$HUBBLE_VERSION/hubble-linux-amd64.tar.gz

tar xzvf hubble-linux-amd64.tar.gz

mv hubble /usr/local/bin/

# 开启端口转发访问 Hubble

cilium hubble port-forward &

# 查看实时流量

hubble observe –namespace production

# Feb 20 10:01:01.000: production/frontend:45678 -> production/backend:8080 http-response FORWARDED

# Feb 20 10:01:01.001: production/backend:8080 -> production/frontend:45678 http-request FORWARDED

# 查看 DNS 流量

hubble observe –protocol DNS

# 查看被 drop 的包

hubble observe –verdict DROPPED

# Hubble UI(Web 界面)

cilium hubble ui  # 自动打开浏览器,展示服务间流量拓扑图

5.3 Cilium L7 网络策略

YAML

# L7 HTTP 策略(Calico 和 Flannel 做不到!)

apiVersion: “cilium.io/v2”

kind: CiliumNetworkPolicy

metadata:

 name: l7-http-policy

 namespace: production

spec:

 endpointSelector:

   matchLabels:

     app: api-server

 ingress:

 – fromEndpoints:

   – matchLabels:

       app: frontend

   toPorts:

   – ports:

     – port: “8080”

       protocol: TCP

     rules:

       http:

       – method: “GET”

         path: “/api/v1/.*”   # 只允许 GET /api/v1/

       – method: “POST”

         path: “/api/v1/orders”  # POST 只允许下单接口

 egress:

 – toFQDNs:

   – matchName: “api.external.com”  # 只允许访问指定域名!

六、Weave Net / Antrea / 其他插件一览

6.1 Weave Net

BASH

# Weave 安装

kubectl apply -f “https://cloud.weave.works/k8s/net?k8s-version=$(kubectl version | base64 | tr -d ‘

‘)”

# Weave 特性:

# – 全 mesh 对等连接,每个节点和其他所有节点直接连

# – 支持加密通信(–password 参数)

# – Fast Datapath:内核 OVS 加速,减少用户态拷贝

# 查看 Weave 状态

kubectl exec -n kube-system weave-net-xxxxx -c weave — /home/weave/weave –local status

# Connections:

#   -> 192.168.1.102:6783  established

#   -> 192.168.1.103:6783  established

6.2 Antrea(VMware/国产常用)

BASH

# Antrea 安装

kubectl apply -f https://github.com/antrea-io/antrea/releases/latest/download/antrea.yaml

# Antrea 特性:

# – 基于 OVS(Open vSwitch)实现,功能强大

# – 支持 NetworkPolicy Tier(优先级分层策略)

# – 内置 Traceflow(数据包追踪,类似 Calico flow log)

# – Octant UI 可视化

# 查看 Antrea 状态

kubectl exec -n kube-system deploy/antrea-controller — antctl get featuregates

# 查看 OVS 流表(在节点上)

ovs-vsctl show

ovs-ofctl dump-flows br-int | head -30

插件 推荐场景 网络模式 特色功能
Flannel 开发/测试环境
简单集群
VXLAN/host-gw 安装最简单
Calico 生产环境
大规模集群
BGP/IPIP/VXLAN NetworkPolicy 最强
Cilium 高性能生产
可观测需求强
eBPF native L7 策略/无需 sidecar
Weave 小集群/加密需求 VXLAN full-mesh 开箱即用/加密通信
Antrea VMware 环境
国产信创
OVS/Geneve 可视化/Traceflow

七、云原生网络插件(云厂商专属)

云厂商 插件名称 底层实现 特色
AWS(EKS) amazon-vpc-cni VPC 弹性网卡(ENI) Pod IP = VPC 真实 IP,无 Overlay
阿里云(ACK) terway 弹性网卡/NetworkPolicy 支持独占 ENI,延迟最低
腾讯云(TKE) tke-route-eni VPC 路由 + ENI 支持多网卡,适合高性能
Azure(AKS) azure-cni VNet 虚拟子网 Pod 直接使用 VNet IP
GCP(GKE) google-cloud-cni VPC native Pod IP 可直接被 GCP LB 路由
华为云(CCE) canal / vpc-cni VPC 路由 支持 GPU 节点加速网络
☁️ 云原生插件核心优势
• Pod IP 直接使用云厂商 VPC 的真实 IP,无 NAT 无 Overlay
• 网络性能等同于云主机间直连,延迟极低
• 安全组直接管控 Pod 流量(VPC 级别策略)
• 缺点:Pod 密度受 ENI 数量限制
BASH

# 阿里云 Terway 配置示例

# 模式 1:VPC 路由模式(兼容性好)

# 模式 2:独占 ENI 模式(性能最好)

# 模式 3:ENI 多 IP 模式(密度最高)

# 查看 Terway 模式

kubectl get cm -n kube-system eni-config -o yaml

# 查看 ENI 分配状态

kubectl get felixconfiguration -n kube-system

kubectl describe node <node-name> | grep -E ‘ENI|IP’

# AWS VPC CNI:调整每节点最大 Pod 数

# 默认每节点 Pod 数受 ENI * (max_ip_per_eni – 1) 限制

kubectl set env daemonset aws-node -n kube-system \

 ENABLE_PREFIX_DELEGATION=true \  # 前缀委托,突破 IP 限制

 WARM_PREFIX_TARGET=1

八、网络插件常见问题与排查

8.1 Pod 无法通信排查流程

排查决策树:

Pod 无法访问其他 Pod?
│
├─► 能 ping 同节点 Pod?
│     ├─ 否 → 检查 cni0/cbr0 网桥配置,查 CNI 日志
│     └─ 是 → 能 ping 跨节点 Pod?
│                 ├─ 否 → 检查节点路由/隧道,检查防火墙端口(VXLAN:8472,IPIP:4,BGP:179)
│                 └─ 是 → 能访问 Service ClusterIP?
│                              ├─ 否 → kube-proxy/eBPF 问题,检查 iptables/ipvs 规则
│                              └─ 是 → 检查 DNS(CoreDNS)
│
Pod 无法获取 IP?
│
├─► kubectl describe pod 查 Events
│     ├─ "failed to create pod network: xxx" → CNI 插件本身问题
│     ├─ "no IP addresses available" → IPAM 耗尽
│     └─ "plugin not found" → /opt/cni/bin/ 插件缺失
BASH

# ===== 常用排查命令大全 =====

# 1. 查看 Pod IP 分配情况

kubectl get pod -o wide -A | grep -v Running

# 2. 查看 CNI 日志(以 Calico 为例)

kubectl logs -n calico-system -l app=calico-node –tail=50

kubectl logs -n kube-flannel -l app=flannel –tail=50

# 3. 在 Pod 内测试网络

kubectl exec -it <pod> — sh -c “ping -c 3 <target-ip>”

kubectl exec -it <pod> — sh -c “curl -v http://<service>:port”

kubectl exec -it <pod> — sh -c “nslookup kubernetes.default”

# 4. 查看节点路由表

ip route show

bridge link show

ip link show

# 5. 查看 iptables 规则(kube-proxy 模式)

iptables-save | grep <service-clusterip>

iptables -t nat -L KUBE-SERVICES -n | grep <service-name>

# 6. 查看 IPVS 规则(kube-proxy IPVS 模式)

ipvsadm -Ln | grep -A3 <service-clusterip>

# 7. 抓包分析

# 在节点上抓 VXLAN 包

tcpdump -i eth0 -nn port 8472

# 在 Pod 内抓包

kubectl exec -it <pod> — tcpdump -i eth0 -nn

# 8. 检查 NetworkPolicy 是否误拦截

kubectl describe networkpolicy -A

# Calico 工具查看策略

kubectl exec -n calico-system calico-node-xxx — calico-node -show-policy-list

# 9. Cilium 专用诊断

cilium connectivity test

cilium-health status

hubble observe –verdict DROPPED –last 100

8.2 常见故障与解决方案

故障现象 常见原因 解决方案
Pod 一直 ContainerCreating
Events: network plugin not ready
CNI 插件未就绪
kubelet 还没初始化完成
等待 CNI DaemonSet 全部就绪
kubectl get ds -A
跨节点 Pod ping 不通 VXLAN 端口(8472)被防火墙阻断
或 BGP 端口(179)被阻断
firewall-cmd 或安全组开放对应端口
DNS 解析失败
nslookup 超时
CoreDNS Pod 异常
或 iptables NAT 规则缺失
kubectl rollout restart deploy coredns -n kube-system
Pod IP 耗尽 no IP available Pod CIDR 规划太小
或有泄漏的僵尸 IP
扩大 podCIDR,清理残留 Pod/IP
Service ClusterIP 无法访问 kube-proxy 未运行
iptables 规则被清空
检查 kube-proxy DaemonSet
iptables-restore 重建规则
MTU 导致大包丢失 Overlay 封装后 MTU 不一致 Flannel: FLANNEL_MTU=1450
Calico: ip link set mtu 1480 dev eth0

九、如何选择网络插件?

场景 推荐插件 理由
学习 / 开发测试 Flannel VXLAN 安装最简单,零配置
生产环境(裸机/VM) Calico BGP 高性能 + 强 NetworkPolicy
生产环境(高性能要求) Cilium eBPF 最高性能 + 可观测性 + L7 策略
公有云(AWS/阿里云) 云原生 CNI(VPC-CNI/Terway) Pod IP = VPC IP,无 Overlay 最快
合规 / 加密传输 Calico WireGuard 或 Cilium 内置 WireGuard 加密所有 Pod 流量
超大规模集群 (1000+ 节点) Calico + Typha 或 Cilium Typha 缓解 API Server 压力
服务网格替代 / 无 Sidecar Cilium eBPF 内核实现 mTLS/L7 观测
总结决策流程
① 用云?→ 优先选云厂商原生 CNI
② 裸机/VM + 性能优先?→ Calico BGP
③ 极致性能 + 可观测 + L7 策略?→ Cilium
④ 只是想快速跑起来?→ Flannel VXLAN
 

🎯 核心总结

 

   ✦ CNI 是 K8s 网络插件的标准接口,所有插件都遵循 ADD/DEL 调用协议
   ✦ Flannel:入门首选,VXLAN 通用,host-gw 高性能但需同子网
   ✦ Calico:生产主流,BGP 路由无封装,企业级 NetworkPolicy
   ✦ Cilium:eBPF 未来方向,L7 策略 + 可观测性 + 无 Sidecar 服务网格
   ✦ 云环境优先选云原生 CNI,Pod IP = VPC IP,零 Overlay 延迟
 

 

📚 更多干货,欢迎关注「院长技术」

 

🔧 往期推荐:K8s 存储体系 / Prometheus 监控 / Tekton CI/CD 系列