Kubernetes VPA 垂直自动扩缩容完整指南:让 Pod 资源分配更智能
背景介绍
在 Kubernetes 集群中,Pod 的资源配额(CPU 和内存)设置是个难题。配置过高会造成资源浪费,配置过低则会导致容器被 OOM Kill 或 CPU 限流。很多人靠人工估算容器的资源需求,既不准又累人。
Vertical Pod Autoscaler(VPA)是 Kubernetes 生态中专门解决这个问题的工具。它能根据容器的实际使用情况,自动调整 Pod 的资源请求量。和 Horizontal Pod Autoscaler(HPA)不同,VPA 是垂直扩缩容——调整单个 Pod 的资源大小,而不是增加 Pod 副本数。
这篇文章会详细介绍如何在 Kubernetes 集群中部署和配置 VPA,并用实际案例展示其工作原理。
问题描述
假设你有一个 Java 应用容器,最初凭经验分配了 500m CPU 和 512Mi 内存。生产环境中,随着业务量增加,你会发现:
手动调整的痛点:
VPA 就是为了解决这些问题设计的。它能:
详细步骤
1. 环境准备
确保 Kubernetes 集群版本在 1.23 以上,kubectl 命令行工具已安装。
检查集群版本
kubectl version --client
kubectl cluster-info
检查是否有 Metrics Server
kubectl get pods -n kube-system | grep metrics-server
Metrics Server 没装的话需要先装。VPA 依赖 Metrics Server 收集资源指标。
2. 安装 Metrics Server
安装 Metrics Server
kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/latest/download/components.yaml
验证安装
kubectl get pods -n kube-system -l k8s-app=metrics-server
3. 安装 Vertical Pod Autoscaler
VPA 由三个组件构成:Recommender(推荐器)、Updater(更新器)和 Admission Plugin(准入插件)。
克隆 VPA 仓库
git clone https://github.com/kubernetes/autoscaler.git
cd autoscaler/vertical-pod-autoscaler
安装 VPA
kubectl apply -f deploy/vpa-gen.yaml
4. 创建 VPA 资源
创建 VPA 资源配置,让它监控特定的 Deployment:
apiVersion: autoscaling.k8s.io/v1
kind: VerticalPodAutoscaler
metadata:
name: myapp-vpa
namespace: default
spec:
targetRef:
apiVersion: "apps/v1"
kind: Deployment
name: myapp-deployment
updatePolicy:
updateMode: "Auto"
resourcePolicy:
containerPolicies:
- containerName: "*"
minAllowed:
cpu: "100m"
memory: "128Mi"
maxAllowed:
cpu: "4"
memory: "8Gi"
controlledValues: "RequestsAndLimits"
参数说明:
updateMode: "Auto" 表示 VPA 会自动更新 Pod 的资源请求minAllowed 和 maxAllowed 限制资源调整范围controlledValues 指定控制请求值还是限制值5. 部署测试应用
创建测试用的 Deployment:
apiVersion: apps/v1
kind: Deployment
metadata:
name: myapp-deployment
namespace: default
spec:
replicas: 3
selector:
matchLabels:
app: myapp
template:
metadata:
labels:
app: myapp
spec:
containers:
- name: myapp
image: nginx:1.21
resources:
requests:
cpu: "100m"
memory: "128Mi"
limits:
cpu: "200m"
memory: "256Mi"
完整代码示例
完整部署清单,包括 VPA 配置:
vpa-complete-example.yaml
---
apiVersion: v1
kind: Namespace
metadata:
name: vpa-demo
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: demo-app
namespace: vpa-demo
spec:
replicas: 2
selector:
matchLabels:
app: demo
template:
metadata:
labels:
app: demo
spec:
containers:
- name: demo-container
image: polinux/stress:latest
command: ["stress"]
args: ["--cpu", "2", "--vm", "1", "--vm-bytes", "256M"]
resources:
requests:
cpu: "100m"
memory: "128Mi"
limits:
cpu: "500m"
memory: "512Mi"
---
apiVersion: autoscaling.k8s.io/v1
kind: VerticalPodAutoscaler
metadata:
name: demo-app-vpa
namespace: vpa-demo
spec:
targetRef:
apiVersion: "apps/v1"
kind: Deployment
name: demo-app
updatePolicy:
updateMode: "Recreate"
resourcePolicy:
containerPolicies:
- containerName: "demo-container"
minAllowed:
cpu: "50m"
memory: "64Mi"
maxAllowed:
cpu: "8"
memory: "16Gi"
controlledValues: "RequestsAndLimits"
部署并查看 VPA 推荐值:
部署应用
kubectl apply -f vpa-complete-example.yaml
查看 VPA 推荐值
kubectl get vpa demo-app-vpa -n vpa-demo -o yaml
查看 VPA 状态
kubectl describe vpa demo-app-vpa -n vpa-demo
运行结果
部署完成后,VPA 会持续监控 Pod 的资源使用情况。几分钟后,可以通过以下命令查看推荐值:
查看 VPA 状态和推荐值
kubectl get vpa -n vpa-demo demo-app-vpa -o jsonpath='{.status.recommendation}' | jq .
典型输出:
{
"containerRecommendations": [
{
"containerName": "demo-container",
"lowerBound": {
"cpu": "150m",
"memory": "192Mi"
},
"target": {
"cpu": "350m",
"memory": "384Mi"
},
"upperBound": {
"cpu": "800m",
"memory": "768Mi"
},
"uncappedTarget": {
"cpu": "350m",
"memory": "384Mi"
}
}
]
}
含义说明:
target:VPA 推荐的资源请求值lowerBound:最小推荐值,低于此值 VPA 不会触发更新upperBound:最大推荐值,超过此值才会在下次检查时触发更新uncappedTarget:不考虑 maxAllowed 限制的理论推荐值使用 updateMode: "Recreate" 时,VPA 会自动删除并重建 Pod 以应用新资源值。使用 updateMode: "Auto" 时,VPA 会在 Pod 重启时自动应用新值。
总结
VPA 为 Kubernetes 资源管理提供了智能化的解决方案。学完这篇文章,你应该已经掌握:
VPA 最适合用于:
不太适合用于:
VPA 可以和 HPA 配合使用,实现水平和垂直双向扩缩容,构建更智能的弹性伸缩架构。