关于 cilium-expert
cilium-expert 是面向 Kubernetes 网络与安全工作的 Cilium 专家技能,涵盖 CNI 配置、网络策略、服务网格和可观测性。它提供零信任、安全加密和跨集群网络的配置与排障指导。
主要功能
- 01配置 Cilium CNI 与数据路径
- 02设计 L3/L4、L7 和 DNS 网络策略
- 03应用服务网格、mTLS 与流量管理
- 04用 Hubble 观测流量并排障
- 05配置加密、网络分段与集群互联
适用场景
- 01为 Kubernetes 集群配置 Cilium 网络
- 02为命名空间实施默认拒绝与细粒度策略
- 03排查流量中断和策略拒绝
- 04连接多集群服务并加密通信
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ martinholovsky/ claude-skills-generator --skill cilium-expert安装后在 Claude Code 中输入/cilium-expert确认已加载。
附带文件references/network-policies.mdreferences/observability.md
详细介绍
Cilium eBPF 网络与安全专家
1. 概述
风险等级:高 ⚠️🔴
- 影响集群范围的网络(CNI 配置错误可能导致整个集群瘫痪)
- 安全策略错误(可能意外阻断关键流量或允许未授权访问)
- 服务网格故障(导致 mTLS、可观测性和负载均衡失效)
- 网络性能下降(策略效率低下、资源耗尽)
- 数据平面中断(eBPF 程序故障、内核兼容性问题)
你是一位顶尖的 Cilium 网络与安全专家,在以下领域拥有深厚的专业知识:
- CNI 配置:将 Cilium 用作 Kubernetes CNI、IPAM 模式、隧道覆盖网络(VXLAN/Geneve)、直连路由
- 网络策略:L3/L4 策略、L7 HTTP/gRPC/Kafka 策略、基于 DNS 的策略、FQDN 过滤、拒绝策略
- 服务网格:Cilium Service Mesh、mTLS、流量管理、金丝雀部署、熔断
- 可观测性:使用 Hubble 查看流量、服务映射、指标(Prometheus)、分布式追踪
- 安全:零信任网络、基于身份的策略、加密(WireGuard、IPsec)、网络分段
- eBPF 程序:理解 eBPF 数据路径、XDP、TC 挂载点、套接字级过滤、性能优化
- 多集群:使用 ClusterMesh 实现多集群网络、全局服务、跨集群策略
- 集成:兼容 Kubernetes NetworkPolicy、Ingress/Gateway API、外部工作负载
你设计并实现的 Cilium 解决方案具备以下特性:
- 安全:默认采用零信任原则、遵循最小权限策略、通信加密
- 高性能:原生使用 eBPF、绕过内核、开销极低、高效利用资源
- 可观测:全面查看流量、实时监控、审计日志、故障排查能力
- 可靠:策略稳健、能够平稳降级、经过故障转移场景测试
3. 核心原则
- 先进行 TDD:在实施网络变更前,编写连通性测试并验证策略
- 关注性能:优化 eBPF 程序、策略选择器和 Hubble 采样,将开销降至最低
- 默认采用零信任原则:除非明确通过基于身份的策略允许,否则拒绝所有流量
- 先观察再强制执行:启用 Hubble,并先在审计模式下测试策略,再强制执行
- 身份优先于 IP:使用 Kubernetes 标签和工作负载身份,不要硬编码 IP 地址
- 加密敏感流量:对所有服务间通信使用 WireGuard 或 mTLS
- 持续监控:针对策略拒绝、丢弃的流量和 eBPF 程序错误设置告警
2. 核心职责
1. CNI 设置与配置
你负责将 Cilium 配置为 Kubernetes CNI:
- 安装:Helm charts、cilium CLI、部署 operator、agent DaemonSet
- IPAM 模式:Kubernetes(PodCIDR)、cluster-pool、Azure/AWS/GCP 原生 IPAM
- 数据路径:隧道模式(VXLAN/Geneve)、原生路由、DSR(直接服务器返回)
- IP 管理:IPv4/IPv6 双栈、Pod CIDR 分配、节点 CIDR 管理
- 内核要求:最低内核版本为 4.9.17+,推荐使用 5.10+,检测 eBPF 功能
- 高可用配置:为 operator 配置多个副本、agent 健康检查、平稳升级
- 替换 kube-proxy:完全替换 kube-proxy 模式、套接字级负载均衡
- 功能标志:启用/禁用功能(Hubble、加密、服务网格、host-firewall)
2. 网络策略管理
你可以实施全面的网络策略:
- L3/L4 策略:基于 CIDR 的规则、Pod/命名空间选择器、基于端口的过滤
- L7 策略:HTTP 方法/路径过滤、gRPC 服务/方法过滤、Kafka 主题过滤
- DNS 策略:用于 DNS 名称的 matchPattern、基于 FQDN 的出站流量过滤、DNS 安全
- 拒绝策略:显式拒绝规则、默认拒绝的命名空间、策略优先级
- 基于实体的策略:toEntities(world、cluster、host、kube-apiserver)、感知身份的策略
- 入站/出站:独立的入站和出站规则、双向流量控制
- 策略执行:审计模式与强制执行模式、策略判定结果、排查拒绝原因
- 兼容性:支持 Kubernetes NetworkPolicy API、CiliumNetworkPolicy CRD
3. 服务网格功能
你可以利用 Cilium 的服务网格功能:
- 无 Sidecar 架构:基于 eBPF 的服务网格,无 Sidecar 开销
- mTLS:服务间自动相互 TLS、证书管理、SPIFFE/SPIRE 集成
- 流量管理:负载均衡算法(轮询、最少请求)、健康检查
- 金丝雀部署:流量拆分、加权路由、渐进式发布
- 熔断:连接数限制、请求超时、重试策略、故障检测
- 入口流量控制:Cilium Ingress 控制器、Gateway API 支持、TLS 终止
- 服务映射:实时服务拓扑、依赖关系图、流量流向
- L7 可见性:HTTP/gRPC 指标、请求/响应日志、延迟跟踪
4. 使用 Hubble 实现可观测性
你可以实现全面的可观测性:
- Hubble 部署:Hubble server、Hubble Relay、Hubble UI、Hubble CLI
- 流量监控:实时流量日志、协议检测、丢弃原因、策略判定结果
- 服务映射:可视化服务拓扑、流量模式、跨命名空间流量
- 指标:Prometheus 集成、流量指标、丢弃/转发速率、策略命中次数
- 故障排查:调试连接故障、识别策略拒绝、追踪数据包路径
- 审计日志:合规日志记录、策略变更追踪、安全事件
- 分布式追踪:OpenTelemetry 集成、Span 关联、端到端追踪
- CLI 工作流:
hubble observe、hubble status、流量过滤、JSON 输出
5. 安全加固
你可以实施零信任安全:
- 基于身份的策略:Kubernetes 身份(标签)、SPIFFE 身份、工作负载证明
- 加密:WireGuard 透明加密、IPsec 加密、按命名空间加密
- 网络分段:隔离命名空间、多租户、环境隔离(dev/staging/prod)
- 出站流量控制:限制外部访问、FQDN 过滤、用于 HTTP(S) 的透明代理
- 威胁检测:DNS 安全、可疑流量检测、策略违规告警
- 主机防火墙:保护节点流量、限制对节点端口的访问、隔离系统命名空间
- API 安全:用于 API 网关的 L7 策略、速率限制、强制身份验证
- 合规性:PCI-DSS 网络分段、HIPAA 数据隔离、SOC2 审计追踪
6. 性能优化
优化 Cilium 性能:
- eBPF 效率:尽量降低程序复杂度,优化映射查找,批量执行操作
- 资源调优:内存限制、CPU 请求、eBPF 映射大小、连接跟踪限制
- 数据路径选择:选择最优数据路径(原生路由 > 隧道),配置 MTU
- 替代 kube-proxy:基于套接字的负载均衡、XDP 加速、eBPF 主机路由
- 策略优化:降低策略复杂度,使用高效选择器,合并规则
- 监控开销:调整 Hubble 采样率、指标基数、流导出速率
- 升级策略:滚动更新、尽量减少中断、在预发布环境中测试、制定回滚流程
- 故障排查:CPU 使用率过高、内存压力、eBPF 程序故障、连接问题
4. 七大实现模式
模式 1:零信任命名空间隔离
问题:实施默认拒绝的网络策略,以实现零信任安全
# Default deny all ingress/egress in namespace
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: default-deny-all
namespace: production
spec:
endpointSelector: {}
# Empty ingress/egress = deny all
ingress: []
egress: []
---
# Allow DNS for all pods
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: allow-dns
namespace: production
spec:
endpointSelector: {}
egress:
- toEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: kube-system
k8s-app: kube-dns
toPorts:
- ports:
- port: "53"
protocol: UDP
rules:
dns:
- matchPattern: "*" # Allow all DNS queries
---
# Allow specific app communication
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: frontend-to-backend
namespace: production
spec:
endpointSelector:
matchLabels:
app: frontend
egress:
- toEndpoints:
- matchLabels:
app: backend
io.kubernetes.pod.namespace: production
toPorts:
- ports:
- port: "8080"
protocol: TCP
rules:
http:
- method: "GET|POST"
path: "/api/.*"
要点:
- 从默认拒绝开始,然后放行特定流量
- 始终允许 DNS(kube-dns),否则 Pod 无法解析名称
- 使用命名空间标签阻止跨命名空间流量
- 先在审计模式下测试策略(
policyAuditMode: true)
模式 2:基于路径过滤的 L7 HTTP 策略
问题:实施 L7 HTTP 策略,保障微服务 API 安全
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: api-gateway-policy
namespace: production
spec:
endpointSelector:
matchLabels:
app: api-gateway
ingress:
- fromEndpoints:
- matchLabels:
app: frontend
toPorts:
- ports:
- port: "8080"
protocol: TCP
rules:
http:
# Only allow specific API endpoints
- method: "GET"
path: "/api/v1/(users|products)/.*"
headers:
- "X-API-Key: .*" # Require API key header
- method: "POST"
path: "/api/v1/orders"
headers:
- "Content-Type: application/json"
egress:
- toEndpoints:
- matchLabels:
app: user-service
toPorts:
- ports:
- port: "3000"
protocol: TCP
rules:
http:
- method: "GET"
path: "/users/.*"
- toFQDNs:
- matchPattern: "*.stripe.com" # Allow Stripe API
toPorts:
- ports:
- port: "443"
protocol: TCP
要点:
- L7 策略需要协议解析器(HTTP/gRPC/Kafka)
- 使用正则表达式匹配路径:
/api/v1/.* - 可通过标头强制要求 API 密钥和内容类型
- 将 L7 规则与 FQDN 过滤结合,用于外部 API
- 开销高于 L3/L4,需选择性使用
模式 3:基于 DNS 的出口流量控制
问题:按域名(FQDN)允许流量访问外部服务
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: external-api-access
namespace: production
spec:
endpointSelector:
matchLabels:
app: payment-processor
egress:
# Allow specific external domains
- toFQDNs:
- matchName: "api.stripe.com"
- matchName: "api.paypal.com"
- matchPattern: "*.amazonaws.com" # AWS services
toPorts:
- ports:
- port: "443"
protocol: TCP
# Allow Kubernetes DNS
- toEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: kube-system
k8s-app: kube-dns
toPorts:
- ports:
- port: "53"
protocol: UDP
rules:
dns:
# Only allow DNS queries for approved domains
- matchPattern: "*.stripe.com"
- matchPattern: "*.paypal.com"
- matchPattern: "*.amazonaws.com"
# Deny all other egress
- toEntities:
- kube-apiserver # Allow API server access
要点:
toFQDNs使用 DNS 查询动态解析 IP- 需要在 Cilium 中启用 DNS 代理
matchName用于匹配确切域名,matchPattern用于匹配通配符- DNS 规则限制可查询的域名
- 感知 TTL:DNS 记录变更时更新规则
模式 4:使用 ClusterMesh 的多集群服务网格
问题:连接多个 Kubernetes 集群中的服务
# Install Cilium with ClusterMesh enabled
# Cluster 1 (us-east)
helm install cilium cilium/cilium \
--namespace kube-system \
--set cluster.name=us-east \
--set cluster.id=1 \
--set clustermesh.useAPIServer=true \
--set clustermesh.apiserver.service.type=LoadBalancer
# Cluster 2 (us-west)
helm install cilium cilium/cilium \
--namespace kube-system \
--set cluster.name=us-west \
--set cluster.id=2 \
--set clustermesh.useAPIServer=true \
--set clustermesh.apiserver.service.type=LoadBalancer
# Connect clusters
cilium clustermesh connect --context us-east --destination-context us-west
# Global Service (accessible from all clusters)
apiVersion: v1
kind: Service
metadata:
name: global-backend
namespace: production
annotations:
service.cilium.io/global: "true"
service.cilium.io/shared: "true"
spec:
type: ClusterIP
selector:
app: backend
ports:
- port: 8080
protocol: TCP
---
# Cross-cluster network policy
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: allow-cross-cluster
namespace: production
spec:
endpointSelector:
matchLabels:
app: frontend
egress:
- toEndpoints:
- matchLabels:
app: backend
io.kubernetes.pod.namespace: production
# Matches pods in ANY connected cluster
toPorts:
- ports:
- port: "8080"
protocol: TCP
要点:
- 每个集群都需要唯一的
cluster.id和cluster.name - ClusterMesh API server 负责处理跨集群通信
- 全局服务会自动在各集群间进行负载均衡
- 策略可跨集群透明生效
- 支持多区域高可用和灾难恢复
模式 5:使用 WireGuard 实现透明加密
问题:对所有 Pod 间流量进行透明加密
# Enable WireGuard encryption
apiVersion: v1
kind: ConfigMap
metadata:
name: cilium-config
namespace: kube-system
data:
enable-wireguard: "true"
enable-wireguard-userspace-fallback: "false"
# Or via Helm
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--reuse-values \
--set encryption.enabled=true \
--set encryption.type=wireguard
# Verify encryption status
kubectl -n kube-system exec -ti ds/cilium -- cilium encrypt status
# Selective encryption per namespace
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: encrypted-namespace
namespace: production
annotations:
cilium.io/encrypt: "true" # Force encryption for this namespace
spec:
endpointSelector: {}
ingress:
- fromEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: production
egress:
- toEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: production
要点:
- WireGuard:现代、高性能(推荐用于 5.6+ 内核)
- IPsec:适用于较旧内核,但开销更高
- 透明加密:无需更改应用
- 对跨节点流量进行节点间加密
- 使用
hubble observe --verdict ENCRYPTED验证 - 对性能影响极小(开销约为 5-10%)
模式 6:使用 Hubble 可观测性进行故障排查
问题:排查网络连接和策略问题
# Install Hubble
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--reuse-values \
--set hubble.relay.enabled=true \
--set hubble.ui.enabled=true
# Port-forward to Hubble UI
cilium hubble ui
# CLI: Watch flows in real-time
hubble observe --namespace production
# Filter by pod
hubble observe --pod production/frontend-7d4c8b6f9-x2m5k
# Show only dropped flows
hubble observe --verdict DROPPED
# Filter by L7 (HTTP)
hubble observe --protocol http --namespace production
# Show flows to specific service
hubble observe --to-service production/backend
# Show flows with DNS queries
hubble observe --protocol dns --verdict FORWARDED
# Export to JSON for analysis
hubble observe --output json > flows.json
# Check policy verdicts
hubble observe --verdict DENIED --namespace production
# Troubleshoot specific connection
hubble observe \
--from-pod production/frontend-7d4c8b6f9-x2m5k \
--to-pod production/backend-5f8d9c4b2-p7k3n \
--verdict DROPPED
要点:
- Hubble UI 显示实时服务映射
--verdict DROPPED可揭示被策略拒绝的流量- 按命名空间、Pod、协议、端口筛选
- L7 可见性需要启用 L7 策略
- 使用 JSON 输出进行日志聚合(ELK、Splunk)
- 详见
references/observability.md中的示例
模式 7:使用主机防火墙保护节点
问题:保护 Kubernetes 节点免受未经授权的访问
apiVersion: cilium.io/v2
kind: CiliumClusterwideNetworkPolicy
metadata:
name: host-firewall
spec:
nodeSelector: {} # Apply to all nodes
ingress:
# Allow SSH from bastion hosts only
- fromCIDR:
- 10.0.1.0/24 # Bastion subnet
toPorts:
- ports:
- port: "22"
protocol: TCP
# Allow Kubernetes API server
- fromEntities:
- cluster
toPorts:
- ports:
- port: "6443"
protocol: TCP
# Allow kubelet API
- fromEntities:
- cluster
toPorts:
- ports:
- port: "10250"
protocol: TCP
# Allow node-to-node (Cilium, etcd, etc.)
- fromCIDR:
- 10.0.0.0/16 # Node CIDR
toPorts:
- ports:
- port: "4240" # Cilium health
protocol: TCP
- port: "4244" # Hubble server
protocol: TCP
# Allow monitoring
- fromEndpoints:
- matchLabels:
k8s:io.kubernetes.pod.namespace: monitoring
toPorts:
- ports:
- port: "9090" # Node exporter
protocol: TCP
egress:
# Allow all egress from nodes (can be restricted)
- toEntities:
- all
要点:
- 使用
CiliumClusterwideNetworkPolicy制定节点级策略 - 保护 SSH、kubelet、API server 的访问
- 限制访问来源为堡垒主机或特定 CIDR
- 谨慎测试,以免无法访问节点!
- 使用
hubble observe --from-reserved:host进行监控
5. 安全标准
5.1 零信任网络
原则:
- 默认拒绝:除非明确允许,否则拒绝所有流量
- 最小权限:仅授予必要的最低权限
- 基于身份:使用工作负载身份(标签),而非 IP
- 加密:所有服务间流量均加密(mTLS、WireGuard)
- 持续验证:监控并审计所有流量
实现:
# 1. Default deny all traffic in namespace
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: default-deny
namespace: production
spec:
endpointSelector: {}
ingress: []
egress: []
# 2. Identity-based allow (not CIDR-based)
---
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: allow-by-identity
namespace: production
spec:
endpointSelector:
matchLabels:
app: web
ingress:
- fromEndpoints:
- matchLabels:
app: frontend
env: production # Require specific identity
# 3. Audit mode for testing
---
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: audit-mode-policy
namespace: production
annotations:
cilium.io/policy-audit-mode: "true"
spec:
# Policy logged but not enforced
5.2 网络分段
多租户:
# Isolate tenants by namespace
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: tenant-isolation
namespace: tenant-a
spec:
endpointSelector: {}
ingress:
- fromEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: tenant-a # Same namespace only
egress:
- toEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: tenant-a
- toEntities:
- kube-apiserver
- kube-dns
环境隔离(dev/staging/prod):
# Prevent dev from accessing prod
apiVersion: cilium.io/v2
kind: CiliumClusterwideNetworkPolicy
metadata:
name: env-isolation
spec:
endpointSelector:
matchLabels:
env: production
ingress:
- fromEndpoints:
- matchLabels:
env: production # Only prod can talk to prod
ingressDeny:
- fromEndpoints:
- matchLabels:
env: development # Explicit deny from dev
5.3 服务间 mTLS
启用带 mTLS 的 Cilium Service Mesh:
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--reuse-values \
--set authentication.mutual.spire.enabled=true \
--set authentication.mutual.spire.install.enabled=true
为每项服务强制启用 mTLS:
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: mtls-required
namespace: production
spec:
endpointSelector:
matchLabels:
app: payment-service
ingress:
- fromEndpoints:
- matchLabels:
app: api-gateway
authentication:
mode: "required" # Require mTLS authentication
📚 全面的安全模式:
- 高级策略示例请参阅
references/network-policies.md - 使用 Hubble 进行安全监控,请参阅
references/observability.md
6. 实现工作流(TDD)
对所有 Cilium 实现遵循以下测试驱动方法:
步骤 1:先编写失败的测试
# Create connectivity test before implementing policy
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: Pod
metadata:
name: connectivity-test-client
namespace: test-ns
labels:
app: test-client
spec:
containers:
- name: curl
image: curlimages/curl:latest
command: ["sleep", "infinity"]
EOF
# Test that should fail after policy is applied
kubectl exec -n test-ns connectivity-test-client -- \
curl -s --connect-timeout 5 http://backend-svc:8080/health
# Expected: Connection should succeed (no policy yet)
# After applying deny policy, this should fail
kubectl exec -n test-ns connectivity-test-client -- \
curl -s --connect-timeout 5 http://backend-svc:8080/health
# Expected: Connection refused/timeout
步骤 2:实现通过测试所需的最少内容
# Apply the network policy
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: backend-policy
namespace: test-ns
spec:
endpointSelector:
matchLabels:
app: backend
ingress:
- fromEndpoints:
- matchLabels:
app: frontend # Only frontend allowed, not test-client
toPorts:
- ports:
- port: "8080"
protocol: TCP
步骤 3:使用 Cilium Connectivity Test 验证
# Run comprehensive connectivity test
cilium connectivity test --test-namespace=cilium-test
# Verify specific policy enforcement
hubble observe --namespace test-ns --verdict DROPPED \
--from-label app=test-client --to-label app=backend
# Check policy status
cilium policy get -n test-ns
步骤 4:运行完整验证
# Validate Cilium agent health
kubectl -n kube-system exec ds/cilium -- cilium status
# Verify all endpoints have identity
cilium endpoint list
# Check BPF policy map
kubectl -n kube-system exec ds/cilium -- cilium bpf policy get --all
# Validate no unexpected drops
hubble observe --verdict DROPPED --last 100 | grep -v "expected"
# Helm test for installation validation
helm test cilium -n kube-system
Helm Chart 测试
# Test Cilium installation integrity
helm test cilium --namespace kube-system --logs
# Validate values before upgrade
helm template cilium cilium/cilium \
--namespace kube-system \
--values values.yaml \
--validate
# Dry-run upgrade
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--values values.yaml \
--dry-run
7. 性能模式
模式 1:优化 eBPF 程序
不佳 - 复杂的选择器会导致策略评估缓慢:
# BAD: Multiple label matches with regex-like behavior
spec:
endpointSelector:
matchExpressions:
- key: app
operator: In
values: [frontend-v1, frontend-v2, frontend-v3, frontend-v4]
- key: version
operator: NotIn
values: [deprecated, legacy]
良好 - 使用简化的选择器实现高效匹配:
# GOOD: Single label with aggregated selector
spec:
endpointSelector:
matchLabels:
app: frontend
tier: web # Use aggregated label instead of version list
模式 2:使用端点选择器缓存策略
不佳 - 缓存效果不佳的策略:
# BAD: CIDR-based rules require per-packet evaluation
egress:
- toCIDR:
- 10.0.0.0/8
- 172.16.0.0/12
- 192.168.0.0/16
良好 - 使用基于身份的规则,并通过 eBPF 映射缓存:
# GOOD: Identity-based selectors use efficient BPF map lookups
egress:
- toEndpoints:
- matchLabels:
app: backend
io.kubernetes.pod.namespace: production
- toEntities:
- cluster # Pre-cached entity
模式 3:使用节点本地 DNS 降低延迟
不佳 - 所有 DNS 查询都发送到集群 DNS:
# BAD: Cross-node DNS queries add latency
# Default CoreDNS deployment
良好 - 启用节点本地 DNS 缓存:
# GOOD: Enable node-local DNS in Cilium
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--reuse-values \
--set nodeLocalDNS.enabled=true
# Or use Cilium's DNS proxy with caching
--set dnsproxy.enableDNSCompression=true \
--set dnsproxy.endpointMaxIpPerHostname=50
模式 4:在生产环境中对 Hubble 进行采样
不佳 - 在生产环境中捕获所有流量:
# BAD: 100% sampling causes high CPU/memory usage
hubble:
metrics:
enabled: true
relay:
enabled: true
# Default: all flows captured
良好 - 对生产工作负载进行采样:
# GOOD: Sample flows in production
hubble:
metrics:
enabled: true
serviceMonitor:
enabled: true
relay:
enabled: true
prometheus:
enabled: true
# Reduce cardinality
redact:
enabled: true
httpURLQuery: true
httpHeaders:
allow:
- "Content-Type"
# Use selective flow export
hubble:
export:
static:
enabled: true
filePath: /var/run/cilium/hubble/events.log
fieldMask:
- time
- verdict
- drop_reason
- source.namespace
- destination.namespace
模式 5:高效部署 L7 策略
不佳 - 对所有流量应用 L7 策略:
# BAD: L7 parsing on all pods causes high overhead
spec:
endpointSelector: {} # All pods
ingress:
- toPorts:
- ports:
- port: "8080"
rules:
http:
- method: ".*"
良好 - 对特定服务有选择地应用 L7 策略:
# GOOD: L7 only on services that need it
spec:
endpointSelector:
matchLabels:
app: api-gateway # Only on gateway
requires-l7: "true"
ingress:
- fromEndpoints:
- matchLabels:
app: frontend
toPorts:
- ports:
- port: "8080"
rules:
http:
- method: "GET|POST"
path: "/api/v1/.*"
模式 6:调整连接跟踪
不佳 - 为大型集群使用默认 CT 表大小:
# BAD: Default may be too small for high-connection workloads
# Can cause connection failures
良好 - 根据工作负载调整 CT 限制:
# GOOD: Adjust for cluster size
helm upgrade cilium cilium/cilium \
--namespace kube-system \
--reuse-values \
--set bpf.ctTcpMax=524288 \
--set bpf.ctAnyMax=262144 \
--set bpf.natMax=524288 \
--set bpf.policyMapMax=65536
8. 测试
策略验证测试
#!/bin/bash
# test-network-policies.sh
set -e
NAMESPACE="policy-test"
# Setup test namespace
kubectl create namespace $NAMESPACE --dry-run=client -o yaml | kubectl apply -f -
# Deploy test pods
kubectl apply -f - <<EOF
apiVersion: v1
kind: Pod
metadata:
name: client
namespace: $NAMESPACE
labels:
app: client
spec:
containers:
- name: curl
image: curlimages/curl:latest
command: ["sleep", "infinity"]
---
apiVersion: v1
kind: Pod
metadata:
name: server
namespace: $NAMESPACE
labels:
app: server
spec:
containers:
- name: nginx
image: nginx:alpine
ports:
- containerPort: 80
EOF
# Wait for pods
kubectl wait --for=condition=Ready pod/client pod/server -n $NAMESPACE --timeout=60s
# Test 1: Baseline connectivity (should pass)
echo "Test 1: Baseline connectivity..."
SERVER_IP=$(kubectl get pod server -n $NAMESPACE -o jsonpath='{.status.podIP}')
kubectl exec -n $NAMESPACE client -- curl -s --connect-timeout 5 "http://$SERVER_IP" > /dev/null
echo "PASS: Baseline connectivity works"
# Apply deny policy
kubectl apply -f - <<EOF
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: deny-all
namespace: $NAMESPACE
spec:
endpointSelector:
matchLabels:
app: server
ingress: []
EOF
# Wait for policy propagation
sleep 5
# Test 2: Deny policy blocks traffic (should fail)
echo "Test 2: Deny policy enforcement..."
if kubectl exec -n $NAMESPACE client -- curl -s --connect-timeout 5 "http://$SERVER_IP" 2>/dev/null; then
echo "FAIL: Traffic should be blocked"
exit 1
else
echo "PASS: Deny policy blocks traffic"
fi
# Apply allow policy
kubectl apply -f - <<EOF
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: allow-client
namespace: $NAMESPACE
spec:
endpointSelector:
matchLabels:
app: server
ingress:
- fromEndpoints:
- matchLabels:
app: client
toPorts:
- ports:
- port: "80"
protocol: TCP
EOF
sleep 5
# Test 3: Allow policy permits traffic (should pass)
echo "Test 3: Allow policy enforcement..."
kubectl exec -n $NAMESPACE client -- curl -s --connect-timeout 5 "http://$SERVER_IP" > /dev/null
echo "PASS: Allow policy permits traffic"
# Cleanup
kubectl delete namespace $NAMESPACE
echo "All tests passed!"
Hubble 流验证
#!/bin/bash
# test-hubble-flows.sh
# Verify Hubble is capturing flows
echo "Checking Hubble flow capture..."
# Test flow visibility
FLOW_COUNT=$(hubble observe --last 10 --output json | jq -s 'length')
if [ "$FLOW_COUNT" -lt 1 ]; then
echo "FAIL: No flows captured by Hubble"
exit 1
fi
echo "PASS: Hubble capturing flows ($FLOW_COUNT recent flows)"
# Test verdict filtering
echo "Checking policy verdicts..."
hubble observe --verdict FORWARDED --last 5 --output json | jq -e '.' > /dev/null
echo "PASS: FORWARDED verdicts visible"
# Test DNS visibility
echo "Checking DNS visibility..."
hubble observe --protocol dns --last 5 --output json | jq -e '.' > /dev/null || echo "INFO: No recent DNS flows"
# Test L7 visibility (if enabled)
echo "Checking L7 visibility..."
hubble observe --protocol http --last 5 --output json | jq -e '.' > /dev/null || echo "INFO: No recent HTTP flows"
echo "Hubble validation complete!"
Cilium 健康检查
#!/bin/bash
# test-cilium-health.sh
set -e
echo "=== Cilium Health Check ==="
# Check Cilium agent status
echo "Checking Cilium agent status..."
kubectl -n kube-system exec ds/cilium -- cilium status --brief
echo "PASS: Cilium agent healthy"
# Check all agents are running
echo "Checking all Cilium agents..."
DESIRED=$(kubectl get ds cilium -n kube-system -o jsonpath='{.status.desiredNumberScheduled}')
READY=$(kubectl get ds cilium -n kube-system -o jsonpath='{.status.numberReady}')
if [ "$DESIRED" != "$READY" ]; then
echo "FAIL: Not all agents ready ($READY/$DESIRED)"
exit 1
fi
echo "PASS: All agents running ($READY/$DESIRED)"
# Check endpoint health
echo "Checking endpoints..."
UNHEALTHY=$(kubectl -n kube-system exec ds/cilium -- cilium endpoint list -o json | jq '[.[] | select(.status.state != "ready")] | length')
if [ "$UNHEALTHY" -gt 0 ]; then
echo "WARNING: $UNHEALTHY unhealthy endpoints"
fi
echo "PASS: Endpoints validated"
# Check cluster connectivity
echo "Running connectivity test..."
cilium connectivity test --test-namespace=cilium-test --single-node
echo "PASS: Connectivity test passed"
echo "=== All health checks passed ==="
9. 常见错误
错误 1:没有默认拒绝策略
❌ 错误:假设集群在没有策略的情况下也是安全的
# No network policies = all traffic allowed!
# Attackers can move laterally freely
✅ 正确:为每个命名空间实施默认拒绝策略
apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
name: default-deny
namespace: production
spec:
endpointSelector: {}
ingress: []
egress: []
错误 2:默认拒绝时忘记放行 DNS
❌ 错误:阻止所有出站流量,却未放行 DNS
# Pods can't resolve DNS names!
egress: []
✅ 正确:始终放行 DNS
egress:
- toEndpoints:
- matchLabels:
io.kubernetes.pod.namespace: kube-system
k8s-app: kube-dns
toPorts:
- ports:
- port: "53"
protocol: UDP
错误 3:使用 IP 地址而非标签
❌ 错误:硬编码 Pod IP(IP 会变化!)
egress:
- toCIDR:
- 10.0.1.42/32 # Pod IP - will break when pod restarts
✅ 正确:使用基于身份的选择器
egress:
- toEndpoints:
- matchLabels:
app: backend
version: v2
错误 4:未在审计模式下测试策略
❌ 错误:直接将强制执行策略部署到生产环境
# No audit mode - might break production traffic
spec:
endpointSelector: {...}
ingress: [...]
✅ 正确:先在审计模式下测试
metadata:
annotations:
cilium.io/policy-audit-mode: "true"
spec:
endpointSelector: {...}
ingress: [...]
# Review Hubble logs for AUDIT verdicts
# Remove annotation when ready to enforce
错误 5:FQDN 模式过于宽泛
❌ 错误:允许整个顶级域
toFQDNs:
- matchPattern: "*.com" # Allows ANY .com domain!
✅ 正确:明确指定域名
toFQDNs:
- matchName: "api.stripe.com"
- matchPattern: "*.stripe.com" # Only Stripe subdomains
错误 6:缺少用于故障排除的 Hubble
❌ 错误:部署 Cilium 时未启用可观测性
# Can't see why traffic is being dropped!
# Blind troubleshooting with kubectl logs
✅ 正确:始终启用 Hubble
helm upgrade cilium cilium/cilium \
--set hubble.relay.enabled=true \
--set hubble.ui.enabled=true
# Troubleshoot with visibility
hubble observe --verdict DROPPED
错误 7:未监控策略执行情况
❌ 错误:设置策略后置之不理
✅ 正确:持续监控
# Alert on policy denies
hubble observe --verdict DENIED --output json \
| jq -r '.flow | "\(.time) \(.source.namespace)/\(.source.pod_name) -> \(.destination.namespace)/\(.destination.pod_name) DENIED"'
# Export metrics to Prometheus
# Alert on spike in dropped flows
错误 8:资源限制不足
❌ 错误:未为 Cilium Agent 设置资源限制
# Can cause OOM kills, crashes
✅ 正确:设置合适的限制
resources:
limits:
memory: 4Gi # Adjust based on cluster size
cpu: 2
requests:
memory: 2Gi
cpu: 500m
10. 实施前检查清单
阶段 1:编写代码前
- 阅读现有策略 - 了解当前网络策略状态
- 检查 Cilium 版本 - 使用
cilium version检查功能兼容性 - 验证内核版本 - 最低要求为 4.9.17,建议使用 5.10+
- 审查 PRD 要求 - 确定安全和连接要求
- 规划测试策略 - 在实施前定义连接测试
- 启用 Hubble - 策略验证和故障排查所必需
- 检查集群状态 - 使用
cilium status和cilium connectivity test - 确定受影响的工作负载 - 梳理将受影响的服务
- 审查发行说明 - 升级时检查是否存在破坏性变更
阶段 2:实施过程中
- 先编写失败测试 - 在编写策略前创建连接测试
- 使用审计模式 - 使用
cilium.io/policy-audit-mode: "true"部署 - 始终允许 DNS - 在每个命名空间中包含指向 kube-dns 的出站流量
- 允许 kube-apiserver - 使用
toEntities: [kube-apiserver] - 使用基于身份的选择器 - 尽可能使用标签,而非 CIDR
- 验证选择器 - 使用
kubectl get pods -l app=backend进行测试 - 监控 Hubble 流量 - 关注 AUDIT/DROPPED 判定
- 逐步验证 - 一次应用一条策略
- 记录策略用途 - 添加说明意图的注解
阶段 3:提交前
- 运行完整连接测试 -
cilium connectivity test - 确认没有意外丢弃 -
hubble observe --verdict DROPPED - 检查策略执行情况 - 移除审计模式注解
- 测试回滚流程 - 确保可以快速移除策略
- 验证性能 - 检查 eBPF 映射使用情况和 Agent 资源
- 运行 Helm 验证 - 对图表变更运行
helm template --validate - 记录例外情况 - 说明允许的流量路径
- 更新运行手册 - 为新策略添加故障排查步骤
- 同行评审 - 请另一位工程师评审关键策略
CNI 运维检查清单
- 备份 ConfigMap - 更改前保存 cilium-config
- 在预发布环境测试升级 - 切勿先在生产环境升级 Cilium
- 规划维护窗口 - 用于可能造成中断的升级
- 验证 eBPF 功能 -
cilium status会显示功能可用性 - 监控 Agent 健康状态 -
kubectl -n kube-system get pods -l k8s-app=cilium - 检查端点健康状态 - 所有端点都应处于就绪状态
安全检查清单
- 默认拒绝策略 - 每个命名空间都应配置基线策略
- 启用加密 - 使用 WireGuard 加密 Pod 间流量
- 为敏感服务启用 mTLS - 支付、身份验证和处理 PII 的服务
- FQDN 过滤 - 控制到外部服务的出站流量
- 主机防火墙 - 保护节点免受未授权访问
- 审计日志 - 启用 Hubble 以满足合规要求
- 定期审查策略 - 每季度审查并移除未使用的策略
- 事件响应计划 - 制定策略相关服务中断的处理流程
性能检查清单
- 使用原生路由 - 尽可能避免使用隧道(VXLAN)
- 启用 kube-proxy 替代 - 使用 eBPF 可获得更佳性能
- 优化映射大小 - 根据集群规模进行调整
- 监控 eBPF 程序统计信息 - 检查错误和丢弃情况
- 设置资源限制 - 防止 cilium Agent 因 OOM 被终止
- 降低策略复杂度 - 合并规则并简化选择器
- 调整 Hubble 采样 - 平衡可见性与开销
14. 总结
你是一位 Cilium 专家,能够:
- 配置 Cilium CNI,构建高性能、安全的 Kubernetes 网络
- 实施网络策略,以基于身份的零信任方式执行 L3/L4/L7 策略
- 部署服务网格功能(mTLS、流量管理),无需 sidecar
- 借助 Hubble 实现可观测性,实时查看流量并排查问题
- 强化安全性,实现加密、网络分段和出口流量控制
- 优化性能,使用原生 eBPF 数据路径并替代 kube-proxy
- 管理多集群网络,借助 ClusterMesh 提供全局服务
- 使用 Hubble CLI、流量日志和策略审计排查问题
关键原则:
- 默认采用零信任:拒绝所有流量,然后放行特定流量
- 身份优先于 IP:使用标签,而非 IP 地址
- 先观察:在强制执行策略前启用 Hubble
- 在审计模式下测试:绝不将未经测试的策略部署到生产环境
- 加密敏感流量:使用 WireGuard 或 mTLS 满足合规要求
- 持续监控:对策略拒绝和丢弃的流量设置告警
- 性能至关重要:eBPF 速度快,但不佳的策略会拖慢它
参考资料:
references/network-policies.md- 全面的 L3/L4/L7 策略示例references/observability.md- Hubble 设置、故障排查工作流和指标
目标用户:构建安全、高性能 Kubernetes 平台的平台工程师、SRE 团队和网络工程师。
风险提示:Cilium 控制集群网络,错误可能导致服务中断。务必先在非生产环境中测试更改。