如何基于Actuator指标配置K8s HPA实现Spring Boot应用自动扩缩容
1 前置配置:让目标指标可被HPA读取
1.1 配置Spring Boot暴露对应Actuator指标
- 先添加必要依赖,以Maven为例:
<!-- Actuator核心依赖 --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency> <!-- Micrometer Prometheus适配,用于输出Prometheus格式指标 --> <dependency> <groupId>io.micrometer</groupId> <artifactId>micrometer-registry-prometheus</artifactId> </dependency>
- 修改application.yml配置,开启指标暴露和对应指标采集:
management: endpoints: web: exposure: include: prometheus # 暴露prometheus端点 endpoint: prometheus: enabled: true metrics: tags: application: ${spring.application.name} # 给指标加应用名标签,方便Prometheus筛选
启动后访问http://你的服务地址/actuator/prometheus,能搜到jvm_threads_live、jvm_memory_used、process_cpu_usage三个指标即配置成功。
1.2 集群侧配置指标通路
- 首先确保集群已部署Prometheus,且配置了采集规则,能拉取所有Spring Boot实例的
/actuator/prometheus指标。 - 部署Prometheus Adapter,配置规则将三个指标转换为Kubernetes可识别的自定义指标,Adapter的核心规则示例如下(写在Adapter的ConfigMap里):
rules: - seriesQuery: 'jvm_threads_live{namespace!="",pod!=""}' resources: overrides: namespace: {resource: "namespace"} pod: {resource: "pod"} name: {as: "jvm_threads_live"} metricsQuery: 'avg(<<.Series>>{<<.LabelMatchers>>}) by (<<.GroupBy>>)' - seriesQuery: 'jvm_memory_used{namespace!="",pod!="",area="heap"}' resources: overrides: namespace: {resource: "namespace"} pod: {resource: "pod"} name: {as: "jvm_memory_used_heap"} metricsQuery: 'avg(<<.Series>>{<<.LabelMatchers>>}) by (<<.GroupBy>>)' - seriesQuery: 'process_cpu_usage{namespace!="",pod!=""}' resources: overrides: namespace: {resource: "namespace"} pod: {resource: "pod"} name: {as: "process_cpu_usage"} metricsQuery: 'avg(<<.Series>>{<<.LabelMatchers>>}) by (<<.GroupBy>>)'
配置完成后可以执行命令验证指标是否正常暴露:kubectl get --raw "/apis/custom.metrics.k8s.io/v1beta1" | jq . | grep -E "jvm_threads_live|jvm_memory_used_heap|process_cpu_usage"
有输出说明指标通路正常。
2 HPA YAML配置及阈值设置
使用autoscaling/v2版本的HPA API,支持多自定义指标阈值配置,完整示例如下:
apiVersion: autoscaling/v2 kind: HorizontalPodAutoscaler metadata: name: spring-boot-app-hpa namespace: your-namespace # 替换为你的应用所在命名空间 spec: scaleTargetRef: apiVersion: apps/v1 kind: Deployment name: spring-boot-app # 替换为你的应用Deployment名称 minReplicas: 2 # 最小实例数 maxReplicas: 10 # 最大实例数 metrics: # 1. process.cpu.usage阈值:所有实例平均使用率超过70%触发扩容 - type: Pods pods: metric: name: process_cpu_usage target: type: AverageValue averageValue: 0.7 # process_cpu_usage取值范围0-1,0.7对应70%CPU使用率 # 2. jvm.memory.used堆内存阈值:所有实例平均堆内存使用超过1.5G触发扩容 - type: Pods pods: metric: name: jvm_memory_used_heap target: type: AverageValue averageValue: 1500Mi # 3. jvm.threads.live阈值:所有实例平均活动线程数超过200触发扩容 - type: Pods pods: metric: name: jvm_threads_live target: type: AverageValue averageValue: 200 behavior: # 可选,配置扩缩容行为,避免频繁波动 scaleUp: stabilizationWindowSeconds: 60 # 扩容冷却时间1分钟 scaleDown: stabilizationWindowSeconds: 300 # 缩容冷却时间5分钟
配置说明:
- 阈值类型选
AverageValue是指所有当前运行的Pod的指标平均值达到阈值就触发扩缩容,符合大多数业务场景 - 你可以根据实际业务需求调整每个指标的阈值,比如堆内存阈值可以根据JVM的Xmx配置设置为Xmx的70%-80%
- 多指标场景下HPA会取所有指标计算出的期望副本数的最大值作为最终扩缩容目标
部署完成后执行kubectl get hpa -n your-namespace,可以看到TARGETS列显示三个指标的当前值和阈值,说明配置生效。
内容的提问来源于stack exchange,提问作者mimo2000
相关产品推荐
相关产品推荐

