先上demo代码仓库

https://github.com/wentjiang/prometheus-HPA-test

自动扩缩容的使用场景

在开发微服务时,我们会有一些请求量突增的场景,举个例子,快上下班的时候,大家都需要签到签退,那么签到考勤,那么对于考勤服务,在上下班的时候,会出现流量激增的情况,一种解决方法是,我们将服务的数量启动到能满足峰值的情况,这种情况会产生不必要的资源浪费,那么,怎么样才能解决该问题呢?作为云原生时代最重要的基础设施,k8s为我们提供了HPA(Horizontal Pod Autoscaler)自动扩缩容机制,这样我们就能够应对类似的流量突增的情况,按照配置好的扩缩容机制,进行自动的扩缩容;

HPA使用方式及实现原理

k8s原生的HPA使用方式为:

1.使用类似Deployment的方式部署微服务

2.为微服务添加HPA定义

完成以上配置之后,Metrics Server会根据从pod采集到的信息,使用HPA中定义的判断条件,对当前Deployment的副本数进行调整,以达到期望数值

常规的自动扩缩容的局限性

k8s原生的自动扩缩容,支持的指标只有cpu和内存,但我们业务的场景可能使用的不仅限于cpu和内存,或者,cpu和内存不能满足业务扩缩容的需求,这样的话,就需要使用自定义指标的HPA来进行实现,例如,客户端提交的计算任务,服务端使用生产者消费者模式,将客户端的计算任务放在队列中,这个时候,监听队列的积压,从而进行扩缩容是一个相对于cpu,内存来说更优的方案

HPA指标的分类

通过上述的介绍,想必大家已经明白了HPA的原理,和为什么使用自定义指标扩缩容,这里列出几种HPA指标:

HPA需要从metrics API获取到所需要进行HPA的值,默认使用的是metrics server提供的数据,只有cpu,内存的信息,如果要使用service相关的数据,如http get请求数之类的信息,需要查阅外部指标相关的API,k8s也同样支持,这里只关注custom metrics api指标,接下来,我们将详细的了解如何一步一步搭建自定义指标HPA,这里选取主流的prometheus作为采集指标的收集器,将数据上报给HPA

搭建自定义指标HPA环境

前置条件

 k8s集群,helm可用

整体的搭建流程

  1. 部署prometheus在k8s上
  2. 部署service
  3. 在prometheus上配置服务的serviceMonitor
  4. 部署prometheus adapter在k8s上
  5. 配置prometheus的采集规则rule
  6. 为service添加HPA配置
  7. 验证HPA是否生效

使用helm安装prometheus

将prometheus保存到本地,可根据需要修改prometheus配置

helm show values prometheus-community/kube-prometheus-stack > prometheus-config.yaml

这里使用默认的配置进行安装,安装时需要注意,如果之前集群通过helm安装过prometheus,需要将所有之前安装的信息删除掉(包括无状态,有状态,配置,自定义对象等),否则会导致安装失败

使用helm命令安装prometheus,完成之后会有以下输出

$ helm install ops-prometheus prometheus-community/kube-prometheus-stack -n ops
NAME: ops-prometheus
LAST DEPLOYED: Tue Nov  3 16:26:10 2020
NAMESPACE: monitoring
STATUS: deployed
REVISION: 1
NOTES:
kube-prometheus-stack has been installed. Check its status by running:kubectl --namespace monitoring get pods -l "release=ops-prometheus"Visit https://github.com/prometheus-operator/kube-prometheus for instructions on how to create & configure Alertmanager and Prometheus instances using the Operator.
prometheus相关文档(https://github.com/prometheus-operator/kube-prometheus)
验证prometheus是否部署成功
$ kubectl --namespace ops get pods -l "release=ops-prometheus"
NAME                                                   READY   STATUS    RESTARTS   AGE
ops-prometheus-kube-promet-operator-6d44cfccfb-72xv2   2/2     Running   0          52d
ops-prometheus-prometheus-node-exporter-n6fg4          1/1     Running   0          52d# wentao.jiang @ wentjiang in ~/Downloads/temp on git:master x [23:23:03]
$ kubectl get pods -n ops
NAME                                                     READY   STATUS    RESTARTS   AGE
alertmanager-ops-prometheus-kube-promet-alertmanager-0   2/2     Running   0          52d
ops-prometheus-adapter-8ff46679d-c52ch                   1/1     Running   0          51d
ops-prometheus-grafana-f4875b756-zvn6m                   2/2     Running   0          52d
ops-prometheus-kube-promet-operator-6d44cfccfb-72xv2     2/2     Running   0          52d
ops-prometheus-kube-state-metrics-7bdbdb4559-z4dlf       1/1     Running   0          52d
ops-prometheus-prometheus-node-exporter-n6fg4            1/1     Running   0          52d
prometheus-ops-prometheus-kube-promet-prometheus-0       3/3     Running   1          52d
如果所有node中的exporter 都为running状态,并包含以下组件:
- alertmanager-ops-prometheus-kube-promet-alertmanager
- ops-prometheus-grafana
- ops-prometheus-kube-promet-operator
- ops-prometheus-kube-state-metrics
- ops-prometheus-prometheus-node-exporter
- prometheus-ops-prometheus-kube-promet-prometheus
则部署成功

部署demo service

将我们已经写好的demo程序部署到k8s集群中

将代码clone到本地,保证本地环境中有gradle,docker,执行./build.sh 会自动构建出prometheus-test:1.1的镜像,也可以直接使用上传好的docker hub的镜像

docker pull wentjiang/prometheus-test:1.1

启动service,

在项目目录下执行

kubectl create -f ./k8s/service.yaml -n local

分别查看pod 和 service状态

请求以下接口,验证服务启动成功

$ curl http://localhost:8080/prometheus-test/1.0/test
ok%
 

配置prometheus serviceMonitor

配置serviceMonitor的目的是让prometheus能够采集到服务的监控指标

按照代码中的serviceMonitor.yaml的配置,启动serviceMonitor

使用kubectl create -f ./k8s/serviceMonitor.yaml -n local启动

查看serviceMonitor创建成功

部署prometheus adapter

prometheus adapter的作用是让k8s的custome api能够采集到prometheus的监控数据

安装过程中使用该文档     prometheus-adapter参考链接

a.添加adapter仓库

helm repo add prometheus-community https://prometheus-community.github.io/helm-charts
               helm repo update

b.查找prometheus对应的ip,记录下来,adapter配置中需要使用

c.修改adapter的配置项

helm show values prometheus-community/prometheus-adapter > prometheus-adapter.yaml
修改prometheus.url为上边查到的url prometheus:url: http://10.106.240.218port: 9090path: ""

d.安装prometheus adapter chart

helm repo update
helm install [RELEASE_NAME] prometheus-community/prometheus-adapter --values prometheus-adapter.yaml --namespace ops
NAME: prometheus-adapter
LAST DEPLOYED: Wed Nov  4 09:22:09 2020
NAMESPACE: ops
STATUS: deployed
REVISION: 1
TEST SUITE: None
NOTES:
prometheus-adapter has been deployed.
In a few minutes you should be able to list metrics using the following command(s):kubectl get --raw /apis/custom.metrics.k8s.io/v1beta1

e.验证是否部署成功

等待几分钟adapter相关配置安装完成

$ kubectl_local get --raw "/apis/custom.metrics.k8s.io/v1beta1/namespaces/local/pods/*/custom_value"
{"kind":"MetricValueList","apiVersion":"custom.metrics.k8s.io/v1beta1","metadata":{"selfLink":"/apis/custom.metrics.k8s.io/v1beta1/namespaces/local/pods/%2A/custom_value"},"items":[{"describedObject":{"kind":"Pod","namespace":"local","name":"prometheus-test-796fcd758d-5c7fc","apiVersion":"/v1"},"metricName":"custom_value","timestamp":"2020-12-25T13:46:59Z","value":"0","selector":null}]}

看到服务的custom_value已经成功的注册到了k8s的api server上,至此,已经成功的将微服务的自定义指标注册到了k8s集群的api Server上

配置prometheus的采集规则rule

这里的rule是添加adapter采集prometheus数据的规则,需要修改adapter对应的配置

a.找到adapter对应的configmap

$ kubectl_local get configmap -n ops |grep prometheus-adapter
ops-prometheus-adapter                                         1      52d

执行命令进行修改

kubectl edit configmap ops-prometheus-adapter -n ops 

在rule的数组中添加以下规则

    - metricsQuery: avg(rate(<<.Series>>{<<.LabelMatchers>>}[10s])) by (<<.GroupBy>>)name:as: ""matches: custom_valueresources:overrides:namespace:resource: namespacepod_name:resource: podseriesQuery: custom_value{namespace!="",pod_name!=""}

保存之后 adapter会热更新该配置项

为service添加HPA配置

kubectl create ./k8s/hpa.yaml -n local

可以看到配置已经成功提交

验证HPA是否生效

kubectl describe hpa prometheus-test-hpa -n local 可以查看当前hpa的状态

可以看到,当前hpa的状态一切良好, 最小副本数为1,最大副本数为3,当前custom_value的值为 0,目标平均值为10

现在我们修改custom_value的值,使其大于hpa中设置的值,就会看到副本数根据规则增加

调用服务的修改custom_value的接口

持续观察hpa的状态,可以发现,下图中,hpa已经开始工作了,拉起新的节点

已经成功的创建出了第二个节点,图中的5500m实际含义为5500/1000的数值,即为5.5,当前custom_value 11/2=5.5

至此,我们所有的操作都已经完成了

参考资料

k8s官网对于自定义指标支持的文档

https://kubernetes.io/zh/docs/tasks/run-application/horizontal-pod-autoscale/#support-for-custom-metrics

支持自定义指标的适配器

https://github.com/kubernetes/metrics/blob/master/IMPLEMENTATIONS.md#custom-metrics-api

https://www.padok.fr/en/blog/scaling-prometheus-rabbitmq

https://github.com/prometheus-community/helm-charts/tree/main/charts/kube-prometheus-stack

https://artifacthub.io/packages/helm/prometheus-community/prometheus-adapter

k8s自定义指标HPA实践(微服务基于自定义指标自动扩缩容的实践)附demo相关推荐

  1. Kubernetes:HPA 详解-基于 CPU、内存和自定义指标自动扩缩容

    目录 HPA 基本原理 Metrics Server 聚合 API 安装Metrics Server HPA 基于 CPU自动扩缩容 查看 HPA 资源的对象了解工作过程: HPA 基于 内存自动扩缩 ...

  2. 通过Dapr实现一个简单的基于.net的微服务电商系统(十一)——一步一步教你如何撸Dapr之自动扩/缩容...

    上一篇我们讲到了dapr提供的bindings,通过绑定可以让我们的程序轻装上阵,在极端情况下几乎不需要集成任何sdk,仅需要通过httpclient+text.json即可完成对外部组件的调用,这样 ...

  3. K8S集群Pod资源自动扩缩容方案

    K8S集群Pod资源自动扩缩容方案 1.为什么要是有自动扩缩容 在K8S集群中部署的应用程序都是以Pod的形式部署的,我们在部署Pod资源时都会指定Pod资源的副本数,但是这个数量是写死的,平时可能启 ...

  4. k8s自动扩缩容、健康检查、Qos、资源管理、亲和度、污点与宽容

    环境为centos7.9 安装k8s 1.23.1 一.自动扩缩容 1.安装Metrics Server wget https://github.com/kubernetes-sigs/metrics ...

  5. 8.HPA自动扩缩容

    1 什么是HPA? HPA(Horizontal Pod Autoscaler,水平Pod自动伸缩器)可根据观察到的CPU.内存使用率或自定义度量标准来自动扩展或缩容Pod的数量.HPA不适用于无法缩 ...

  6. 22,Horizontal Pod Autoscaler(HPA),自动扩缩容

    在前面的课程中,我们已经可以实现通过手工执行kubectl scale命令实现Pod扩容或缩容,但是这显然不符合Kubernetes的定位目标–自动化.智能化. Kubernetes期望可以实现通过监 ...

  7. 测试Hpa自动扩缩容

    一.Hpa设置 最大pod副本数为5,最小pod副本数为3 平均cpu为10% 二.查看当前pod资源消耗 `kubectl top pod -n test` 三.创建一个service服务,type ...

  8. Serverless Knative Serving弹性扩缩容实践整理

    文章目录 (一)基础 (1)认识 (2)Knative Serving对象模型 (3)knative-serving (4)Knative的扩缩容流程原理 (二)弹性扩缩容实践 (1)自动扩缩容类型选 ...

  9. Kubernetes HPA 动态弹性扩缩容

    1.HPA 1.1HPA介绍 1.在Kubernetes中,HPA自动更新工作负载资源(例如:Deployment或者StatefulSet),目的是自动扩缩工作负载以满足需求,水平扩缩意味着对增加的 ...

最新文章

  1. 分享一下我为什么可以获得ssp
  2. CF908D New Year and Arbitrary Arrangement
  3. Java并发框架——AQS之怎样使用AQS构建同步器
  4. CodeForces - 1301E 1-Trees and Queries(LCA)
  5. CodeForces - 1215C Swap Letters(暴力+思维+模拟)
  6. 计算机应用基础在线作业南开,2017南开计算机应用基础在线作业满分的答案.doc...
  7. Lintcode9 Fizz Buzz solution 题解
  8. Spring boot starter
  9. 在Swing和Swt中使用JavaFX
  10. [css] 使用overflow: scroll时不能平滑滚动怎样解决?
  11. 鸿蒙系统的适配国产手机,真正的好消息!其它国产机,也在适配华为鸿蒙系统...
  12. 从UDP/TCP到HTTP/HTTP2,弄清楚网络层面上应该了解的知识。
  13. 温故js系列(7)-数组去重由慢到快由繁到简
  14. Nginx服务器的开发团队
  15. 如何将松散的dll打包进需要发布的exe
  16. 更改Windows OEM信息
  17. dnspod.cn 动态域名客户端
  18. 从零开始自制实现WebServer(十二)---- 剑指定时器小根堆处理 给EventLoop定时任务处理一个温暖的家
  19. 【防诈骗】QQ账号安全检测工具-腾讯出品
  20. 700页JVM虚拟机实战手册,呕心巨作,值得一看

热门文章

  1. 【Hive】性能调优 - map-side JOIN
  2. 解决CentOS无法解析域名的问题
  3. git push错误解决方案
  4. MacOS~jenkins里解决docker执行权限问题
  5. 解决一个Android Studio gradle的小问题
  6. 如何在Java中将字节数组转换为十六进制字符串?
  7. 您如何计算Visual Studio解决方案中的代码行?
  8. win11原版iso如何安装 Windows11原版iso安装步骤方法
  9. UUID生成唯一激活码
  10. linux将文件的第二列求和,awk实现第一列相乘,第二列求和,并相加 - 米扑博客...