K8s HPA自动扩缩容实战指南
在 Kubernetes(k8s)中,HPA 是 Horizontal Pod Autoscaler(水平 Pod 自动扩缩容) 的缩写,是 k8s 核心的自动弹性伸缩功能之一。它的核心作用是根据 Pod 的实际负载(如 CPU 使用率、请求量等)自动调整 Pod 的数量—— 负载升高时增加 Pod 以应对压力,负载降低时减少 Pod 以节省资源,无需人工干预,是保障服务稳定性和资源效率的关键组件。
一、HPA 的核心特性与工作原理
1. 核心特性
- 水平扩缩容:仅调整 Pod 数量(区别于 VPA 垂直扩缩容 —— 调整单个 Pod 的 CPU / 内存上限)。
- 多指标触发:支持基于「系统指标」(CPU、内存)和「自定义指标」(如 QPS、并发连接数)触发扩缩容。
- 边界控制:可设置「最小 Pod 数」和「最大 Pod 数」,避免扩缩容过度(如缩到 0 导致服务中断,或无限扩容耗尽资源)。
- 动态计算:基于指标与阈值的差值,自动计算需新增 / 删除的 Pod 数量(遵循 k8s 内置的扩缩容算法)。
2. 工作原理
HPA 通过「监控 - 对比 - 计算 - 执行」四步实现自动扩缩容,流程如下:
- 指标采集:通过 k8s 组件(如 Metrics Server、Prometheus)持续采集目标 Pod 的负载指标(如 CPU 使用率)。
- 阈值对比:将采集到的实际指标与用户设定的阈值(如 CPU 使用率 ≥ 70%)进行对比。
- 数量计算:若实际指标超过阈值,按算法计算需新增的 Pod 数;若低于阈值,计算需删除的 Pod 数(需满足 min/max 限制)。
- 执行扩缩容:向 k8s 的 Deployment/StatefulSet 发送指令,创建或删除 Pod,完成弹性调整。
二、实操案例:为 Nginx 服务配置 HPA
假设我们有一个 Nginx Web 服务,部署在 k8s 中,需求是:
- 初始 Pod 数量为 2;
- 当 Pod 的 CPU 使用率超过 70% 时,自动增加 Pod(最多不超过 5 个);
- 当 CPU 使用率低于 30% 时,自动减少 Pod(最少不低于 2 个)。
前提:安装 Metrics Server
HPA 需要通过 Metrics Server 采集 Pod 的 CPU / 内存指标,因此需先安装:
# 安装 Metrics Server(适合 k8s 1.24+ 版本)
kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/latest/download/components.yaml# 验证安装(看到 metrics-server-xxx 运行即可)
kubectl get pods -n kube-system | grep metrics-server
步骤 1:部署 Nginx 服务(Deployment)
首先创建一个 Deployment 管理 Nginx Pod,必须配置 resources.requests
(HPA 需基于此计算指标):
# nginx-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:name: nginx-deploy # Deployment 名称
spec:replicas: 2 # 初始 Pod 数量selector:matchLabels:app: nginx # 匹配 Pod 的标签template:metadata:labels:app: nginx # Pod 标签spec:containers:- name: nginximage: nginx:1.25 # Nginx 镜像ports:- containerPort: 80 # 暴露 80 端口resources:requests: # HPA 指标计算基准(必填)cpu: 100m # 每个 Pod 申请 0.1 CPU 核心memory: 128Mi # 每个 Pod 申请 128MB 内存limits: # Pod 资源上限(可选,防止资源超额)cpu: 200mmemory: 256Mi
执行部署命令
kubectl apply -f nginx-deployment.yaml# 验证 Deployment 和 Pod(看到 2 个 Running 的 Pod 即可)
kubectl get deploy nginx-deploy
kubectl get pods -l app=nginx
步骤 2:创建 HPA 规则
创建 HPA 配置文件,关联上述 Deployment 并定义扩缩容规则:
# nginx-hpa.yaml
apiVersion: autoscaling/v2 # HPA v2 版本(支持多指标,推荐)
kind: HorizontalPodAutoscaler
metadata:name: nginx-hpa # HPA 名称
spec:scaleTargetRef: # 关联的目标资源(这里是 Deployment)apiVersion: apps/v1kind: Deploymentname: nginx-deployminReplicas: 2 # 最小 Pod 数(避免缩到 0)maxReplicas: 5 # 最大 Pod 数(避免无限扩容)metrics: # 触发扩缩容的指标(这里用 CPU 使用率)- type: Resourceresource:name: cpu # 基于 CPU 指标target:type: Utilization # 基于使用率(而非绝对值)averageUtilization: 70 # 阈值:CPU 使用率 ≥ 70% 触发扩容behavior: # 可选:定义扩缩容行为(如避免频繁调整)scaleDown:stabilizationWindowSeconds: 300 # 缩容前等待 5 分钟(防止负载波动)
执行 HPA 创建命令:
kubectl apply -f nginx-hpa.yaml# 验证 HPA(看到 TARGETS 为 <unknown>/70%,等待 10 秒后刷新)
kubectl get hpa nginx-hpa
步骤 3:模拟负载,验证 HPA 扩容
为了触发 HPA 扩容,我们需要给 Nginx Pod 增加 CPU 负载(模拟用户请求激增):
- 进入一个 Nginx Pod:
# 替换 <pod-name> 为实际的 Pod 名称(如 nginx-deploy-7f98d7c6b4-2xqzk) kubectl exec -it <pod-name> -- /bin/bash
- 在 Pod 内执行高负载命令(循环计算,消耗 CPU):
# 这会持续占用 CPU,使使用率超过 70% while true; do :; done
- 观察 HPA 和 Pod 变化:
# 每隔 5 秒刷新 HPA 状态(看到 CURRENT 使用率超过 70%,REPLICAS 从 2 增加到 3/4/5) watch kubectl get hpa nginx-hpa# 同时观察 Pod 数量变化(Pod 数量会随 HPA 指令增加) kubectl get pods -l app=nginx
步骤 4:停止负载,验证 HPA 缩容
- 停止高负载命令:在 Pod 的 bash 终端中按
Ctrl+C
终止循环,或直接退出 Pod 并执行:kubectl delete pod <pod-name> # 删除高负载的 Pod,新建的 Pod 会恢复低负载
- 观察 HPA 和 Pod 变化:
# 等待 5 分钟(对应 stabilizationWindowSeconds: 300),看到 CPU 使用率低于 30%,REPLICAS 从 5 减少到 2 watch kubectl get hpa nginx-hpa
三、常见扩展场景:基于自定义指标的 HPA
除了 CPU / 内存等系统指标,HPA 还支持基于自定义指标(如 “每秒请求数 QPS”“并发连接数”)扩缩容。例如,当 Nginx 的 QPS 超过 1000 时自动扩容,需配合 Prometheus + Adapter 实现(需额外配置指标采集规则),核心 HPA 配置如下:
# 基于 QPS 的 HPA 配置(片段)
metrics:
- type: Externalexternal:metric:name: nginx_http_requests_per_second # 自定义指标:Nginx 每秒请求数selector:matchLabels:app: nginxtarget:type: Valuevalue: 1000 # 阈值:QPS ≥ 1000 触发扩容
总结
HPA 是 k8s 实现 “弹性伸缩” 的核心工具,通过动态调整 Pod 数量,平衡了 “服务稳定性” 和 “资源利用率”。在实际生产中,需结合业务场景选择合适的指标(系统指标 / 自定义指标),并合理设置 min/max 边界和扩缩容行为,避免频繁调整或资源浪费。