流留在哪里,又留了多少
一句话总结
Hubble 把 eBPF 数据路径产生的事件存入节点本地的环形缓冲区,再由 relay 在集群范围内汇总。环形缓冲区会循环覆盖旧数据,因此长期分析必须使用 export。
为什么需要它
开始强制执行策略后,问题会接踵而至。“刚才支付 API 为什么断了?”“这次丢弃是策略造成的,还是路由造成的?”数据路径既然已经进入内核,观测手段也必须在同样的深度上提供。
传统方式是挂上 sidecar 代理来观测请求。每个 Pod 都要附带一个代理,资源开销翻倍,而且要修改 Pod spec,因此还需要重启。Hubble 直接读取已挂在数据路径上的 eBPF 程序所产生的事件,所以既不需要额外的代理,也不需要修改 Pod。
工作原理
结构分为三层。
[eBPF 데이터패스] --perf 링버퍼--> [cilium-agent 안의 Hubble 서버]
gRPC :4244
|
[hubble-relay] :4245
|
+-------------+-------------+
v v
[hubble CLI] [hubble-ui]
由此得出三个运维上很重要的性质。
第一,flow 只在节点本地内存中短暂存在。默认缓冲区为每个节点 4095 个 flow,即使扩大,常用值也是 16383。一个 flow 约占 500 字节,因此 16383 个 flow 在每个节点上大约是 8MiB。流量大的节点可能在几秒内就循环一轮,所以审计证据和事后分析必须配合文件 export。
第二,relay 只是汇总者,不是存储。relay 挂掉,数据路径和节点本地观测都不受任何影响。端口方面,relay 为 4245,节点上的 Hubble 服务器为 4244,指标 endpoint 为 9965。
第三,不存储载荷。flow 是结构化事件,包含源和目的的身份与标签、判定(verdict)、丢弃原因,以及 HTTP/DNS 元数据。如果需要数据包内容,必须使用其他工具。
读懂判定值是实战的关键。
| verdict | 含义 |
|---|---|
| FORWARDED | 已被允许并转发 |
| DROPPED | 被阻断(附带丢弃原因) |
| AUDIT | 处于审计模式;若为强制执行状态则会被阻断的流量 |
| ERROR | 处理过程中出错 |
按丢弃原因整理好最先怀疑的位置,也能节省时间。POLICY_DENIED 表示策略未允许,所以要重新检查身份和端口;CT_MAP_INSERT_FAILED 表示 conntrack map 已满,所以要调整 map 大小;UNSUPPORTED_L3_PROTOCOL 表示非 IP 流量;STALE_OR_UNROUTABLE_IP 表示 ipcache 不一致,所以要检查节点之间的同步。
最后还有一点必须区分。L7 拒绝与 L4 丢弃的日志形态不同。在 L4 被阻断时,连接无法建立,只会留下一行请求记录就结束;而违反 L7 规则时,代理会在已建立的连接之上生成 403 并返回,所以请求记录为 DROPPED,响应记录为 FORWARDED。了解这种不对称之后,只看两行日志就能判断问题出在哪一层。
在现场相遇的样子
我在家庭实验室中部署 Hubble 时,hubble-relay 和 hubble-ui 一直停在 Pending 状态。事件如下。
Warning FailedScheduling 0/1 nodes are available: 1 node(s) had untolerated taint(s).
原因出在调度上。控制平面节点上带有 node-role.kubernetes.io/control-plane:NoSchedule 污点,而 hubble-relay 和 hubble-ui 是 Deployment 而不是 DaemonSet,没有容忍度。与之形成对比的是,CoreDNS 默认带有 control-plane 容忍度,所以能正常启动。worker 节点加入后问题立刻消失,这不是错误,而是正常行为。
这里可以得到一个直觉。Cilium Agent 和 Hubble 服务器每个节点都要有,所以是 DaemonSet;relay 和 UI 整个集群有一个就够了,所以是 Deployment。部署形态不同,调度约束也不同。如果“agent 都已经起来了,只有 hubble CLI 连不上”,就应该先看 relay Pod 的状态。
在同一个集群中设置 L7 策略后得到的日志,与前面模块中看到的完全一样:GET 请求为 FORWARDED,POST 请求为 DROPPED,而针对该 POST 的 403 响应为 FORWARDED。这三行日志就是策略按预期工作的证据。
下一项实验要做什么
编写 Hubble 启用值以及指标和 export 配置,给真实的工作负载添加标签,并用 ConfigMap 整理哪些标签计入身份、哪些被排除,最后做出常用的 flow 过滤查询、丢弃原因诊断表,以及丢弃量激增的告警规则。