使用 `docker stats` 与 `cadvisor` 定位 CPU 热点容器
解读
国内一线/准一线企业在云原生面试中,高频出现“线上 CPU 飙高,如何 5 分钟内定位到具体容器”这一场景题。
面试官真正想考察的是:
- 你是否能在不登录容器内部的前提下,先通过 Docker 原生工具快速缩小范围;
- 你是否知道
docker stats的实时性与字段盲区(无 per-core、无 cgroups v2 细项),并主动补位; - 你是否能把 cadvisor 的多维指标与容器元数据关联,完成二次下钻;
- 你是否具备自动化闭环意识:发现问题→定位根因→记录指标→固化到监控。
答不到“自动化闭环”,基本只能给到中级评分。
知识点
docker stats的采集原理:通过 Docker Engine API 读取 cgroup cpuacct.stat 与 cpu.stat,1 s 刷新一次,字段 CPU % = (delta usage / delta system) × 100。- cgroup v1 与 v2 的 CPU 指标差异:v1 分 cpuacct.usage_percpu、throttling stats;v2 统一为 cpu.stat。
- cadvisor 的容器级 CPU 热点指标:
– container_cpu_usage_seconds_total{cpu=“total|0|1…”},可算 per-core;
– container_cpu_cfs_throttled_periods_total,判断是否被限流;
– container_spec_cpu_quota / period,反推 CPU limit。 - PromQL 定位套路:
rate(container_cpu_usage_seconds_total{name!~“POD|”}[1m])
by (name, id)找出突增容器;再and on (id) increase(container_cpu_cfs_throttled_periods_total[1m]) > 0判断是否因限流导致毛刺。 - 国内混合云场景常见坑:
– 宿主机开启超线程,top 看到的 200% 实际是单核跑满;
– 部分发行版默认挂载cgroup v2,老版本 cadvisor 需加--enable-cgroupv2启动参数;
– 安全合规要求非 root 运行 cadvisor,需加--docker_only --housekeeping_interval=10s降低权限与开销。
答案
现场回答采用“三段式”节奏,总时长控制在 3 分钟,既展示思路又给出可落地命令。
-
30 秒初筛:
docker stats --no-stream --format "table {{.Name}}\t{{.CPUPerc}}\t{{.Container}}" | sort -k2 -hr | head -10
直接输出 CPU 占比最高的容器列表,快速锁定嫌疑容器。 -
90 秒下钻:
若宿主机已部署 cadvisor(国内公司普遍以 DaemonSet 方式跑在 K8s 每个节点),立即在 Prometheus 执行:
topk(5, rate(container_cpu_usage_seconds_total{instance=~"节点IP:8080"}[1m]))
拿到容器 ID 后,再查 per-core 热点:
rate(container_cpu_usage_seconds_total{container_label_com_docker_swarm_service_name="可疑服务"}[1m]) by (cpu)
如果某一核接近 100%,即可判定单线程热点;若所有核均匀上涨,则可能是多线程死循环或频繁 GC。 -
60 秒闭环:
将上述 PromQL 固化成 Grafana 面板,并加告警:
rate(container_cpu_usage_seconds_total[1m]) / on (id) (container_spec_cpu_quota / container_spec_cpu_period) > 0.8
连续 5 min 超过阈值即飞书/钉钉告警卡片附带容器日志链接,实现“定位→通知→复盘”自动化。
如是 Docker Swarm 环境,没有 Prometheus,可直接 curl 节点IP:8080/metrics | grep container_cpu_usage_seconds_total 用本地脚本排序,思路完全一致。
拓展思考
- 当容器 CPU 突增但
docker stats显示正常,需考虑宿主机 steal 时间过高(国内公有云超卖场景)。此时应联合node_cpu_seconds_total{mode="steal"}判断,再决定是否升配或迁移节点。 - 若 cadvisor 指标延迟太大(默认 1 min HouseKeeping),可在启动参数加
--housekeeping_interval=5s --docker_only,但需评估cgroup 接口 QPS对宿主机 1% 以内的额外开销。 - 对于金融级安全要求,cadvisor 不允许宿主机直接暴露 8080,需通过NodeLocal Prometheus + TLS 双向认证采集,避免 metrics 接口泄露容器环境变量。
- 最终极方案是把 CPU 热点指标与持续剖析(pyroscope、parca)联动,实现“指标告警→一键下发 eBPF 火焰图→定位到函数”,把面试答案从“定位容器”提升到“定位代码行”,直接锁定资深专家评级。