1. 简介
在 Kubernetes 中,资源分配与限制的核心原理是 Linux cgroups(Control Groups) 与 内核命名空间(namespaces) 的协同工作:
- namespaces 提供进程、网络、文件系统等隔离视图;
- cgroups 则负责计量和限制 CPU、内存、I/O 等物理资源的使用量。
理解这两层机制,是后续所有资源调优的前提。
2. 资源请求(requests)与限制(limits)
维度 | requests | limits |
语义 | “最少需要” | “最多只能用” |
调度 | kube-scheduler 依据 requests 选择节点 | 不参与调度计算 |
运行时 | 无硬性上限,可超用 | 由 kubelet 写入 cgroups,超限即被限制或杀死 |
结果 | 不设置时默认为 0 | 不设置时默认为节点最大资源 |
典型场景 | 预留资源、保证最小可用 | 防止“吵闹邻居”、保护节点稳定 |
最佳实践:
requests ≈ 应用日常平均负载;
limits ≈ 峰值负载 + 20% 安全余量。
3. CPU 限流关键指标:container_cpu_cfs_periods_total 与 container_cpu_cfs_throttled_periods_total
3.1 指标来源
- 由 kubelet/cAdvisor 暴露,基于 Linux CFS(Completely Fair Scheduler)统计。
- 仅当 Pod 设置了 CPU limits 时才可能出现非零值。
3.2 指标含义
指标 | 释义 | 单位 | 举例 |
container_cpu_cfs_periods_total | 进入 CFS 周期的总次数 | 次 | 10 s 内约 100 次(period=100 ms) |
container_cpu_cfs_throttled_periods_total | 被限流(throttled)的周期次数 | 次 | 100 次里有 40 次被限流 |
3.3 限流比例计算
rate(container_cpu_cfs_throttled_periods_total[5m])
/
rate(container_cpu_cfs_periods_total[5m])
- 0.0:从未被限流,CPU 充足。
- 0.5:一半周期被限流,开始影响延迟。
- >0.8:严重限流,需要提高 limits 或排查业务热点。
3.4 典型现象
- 延迟突刺(P99 抖动)
- 吞吐量下降
- Throttled 次数呈阶梯状上升
4. 各语言运行时资源调优实战
4.1 Java 应用
- 内存
- -Xmx 仅限制 堆,实际 RSS ≈ 堆 + 元空间 + 直接内存 + 本地内存。
- 建议在 limits 上再预留 25% 给非堆与容器开销。
- 使用 -XX:MaxRAMPercentage=75.0 代替固定 -Xmx,让 JVM 自适应容器 cgroup 限制。
- CPU
- JDK8u191+ 已支持 CPU Shares 感知,无需额外参数。
- 若出现频繁 GC 导致 CPU Throttled,可增大 limits 或降低 -XX:ParallelGCThreads。
- 探针
- 健康检查务必加 initialDelaySeconds,防止 JVM 启动期被误杀。
4.2 Go 应用
- GOMAXPROCS
- 默认等于宿主 CPU 核数,容器内会 超限。
- 使用 uber-go/automaxprocs 自动根据 limits 调整:
- import _ "go.uber.org/automaxprocs"
- 内存
- Go 1.19+ 已支持 GOMEMLIMIT 环境变量,可设置与 limits 一致,避免 OOM。
- 若使用 CGO,需再预留 10% 给 C 库。
- 监控
- 关注 process_resident_memory_bytes(RSS)与 go_memstats_heap_inuse_bytes(堆)差值,判断是否频繁 GC。
4.3 Python 应用
- CPU
- GIL 限制多线程并行度,CPU limits 可以适当降低,重点优化 I/O。
- 对于 CPU 密集型任务,使用多进程 + OMP_NUM_THREADS=$CPU_LIMIT。
- 内存
- 解释器自身开销 ≈ 30 MB;大型依赖(numpy、pandas)再额外预留。
- 使用 PYTHONMALLOC=malloc + tracemalloc 定位内存泄漏。
- 镜像
- 使用 python:3.x-slim 或 distroless 把镜像控制在 100 MB 内,减少冷启动延迟。
4.4 PHP 应用
- FPM 进程数
- pm.max_children 建议:
max_children = floor(memory_limit / avg_process_rss) - 确保 memory_limit × max_children < memory limits 的 80%,防止 OOM。
- CPU
- PHP 短生命周期模型,CPU 主要消耗在框架初始化。
- 出现 Throttled 时,优先开启 OPcache(opcache.enable_cli=1)并调大 opcache.memory_consumption。
- 探针
- 利用 FPM 的 /status 端点做就绪探针,避免流量打到未初始化完成的 Pod。
5. 一站式调优流程(Checklist)
阶段 | 动作 | 工具/命令 |
容量规划 | 压测获取 P95/P99 负载 | wrk、hey、locust |
初始值 | 以压测结果设 requests/limits | kubectl apply |
持续监控 | Prometheus + Grafana 看板 | 限流比例、RSS、GC、FPM active processes |
动态调整 | VPA/HPA 自动推荐 | kubectl autoscale / Goldilocks |
兜底策略 | PodDisruptionBudget + PriorityClass | 保证高优业务不被驱逐 |
6. 小结
- requests 保证调度,limits 保护节点。
- Throttled 比例 >0.5 时,优先提升 CPU limits 或优化代码热点。
- 不同语言运行时差异大,需结合监控数据做针对性调优。
- 自动化 > 人工:上线 VPA/HPA,让系统帮你 7×24 调整。
通过以上流程,你可以在保障稳定性的同时,把资源利用率提升 20%–40%,真正做到“降本增效”。