K8s -- 通过自定义prometheus数据实现k8s hpa

转:https://blog.csdn.net/yevvzi/article/details/79561150

核心指标管道

从 Kubernetes 1.8 开始,资源使用指标(如容器 CPU 和内存使用率)通过 Metrics API 在 Kubernetes 中获取。
这些指标可以直接被用户访问(例如通过使用 kubectl top 命令),或由集群中的控制器使用(例如,Horizontal Pod Autoscale
可以使用这些指标作出决策)。

Resource Metrics API

通过 Metrics API,您可以获取指定 node 或 pod 当前使用的资源量。这个 API 不存储指标值,
因此想要获取某个指定 node 10 分钟前的资源使用量是不可能的。

Metrics API 和其他的 API 没有什么不同:

它可以通过与 /apis/metrics.k8s.io/ 路径下的其他 Kubernetes API 相同的端点来发现
它提供了相同的安全性、可扩展性和可靠性保证
Metrics API 在 k8s.io/metrics 仓库中定义。您可以在这里找到关于Metrics API 的更多信息。

注意: Metrics API 需要在集群中部署 Metrics Server。否则它将不可用。

Metrics Server

Metrics Server 实现了Resource Metrics API

Metrics Server 是集群范围资源使用数据的聚合器。
从 Kubernetes 1.8 开始,它作为一个 Deployment 对象默认部署在由 kube-up.sh 脚本创建的集群中。
如果您使用了其他的 Kubernetes 安装方法,您可以使用 Kubernetes 1.7+ (请参阅下面的详细信息)
中引入的 deployment yamls 文件来部署。

Metrics Server 从每个节点上的 Kubelet 公开的 Summary API 中采集指标信息。

通过在主 API server 中注册的 Metrics Server Kubernetes 聚合器 来采集指标信息, 这是在 Kubernetes 1.7 中引入的。

在 设计文档 中可以了解到有关 Metrics Server 的更多信息。

custom metrics api

该API允许消费者访问任意度量描述Kubernetes资源。

API的目的是通过监测管道供应商,在其度量存储解决方案之上实现。

如果你想实现这个API API服务器,请参阅kubernetes-incubator/custom-metrics-apiserver库,其中包含需要建立这样一个API服务器基础设施
其中包含设置这样一个API服务器所需的基本基础设施。

Import Path: k8s.io/metrics/pkg/apis/custom_metrics.

custom metrics apiserver

custom metrics apiserver是为了实现k8s自定义监控指标
的框架。

HPA

自动伸缩是一种根据资源使用情况自动伸缩工作负载的方法。
自动伸缩在Kubernetes中有两个维度:cluster Autoscaler处理节点扩容操作和Horizontal Pod Autoscaler自动缩放rs或rc中的pod。
cluster Autoscaler和Horizontal Pod Autoscaler一起可用于动态调整的计算能力以及并行性的水平,你的系统需要满足sla。
虽然cluster Autoscaler高度依赖于托管集群的云提供商的底层功能,但是HPA可以独立于您的IaaS/PaaS提供商进行操作。

在Kubernetes v1.1中首次引入了hpa特性,自那时起已经有了很大的发展。
hpa第一个版本基于观察到的CPU利用率,后续版本支持基于内存使用。
在Kubernetes 1.6中引入了一个新的API自定义指标API,它允许HPA访问任意指标。
Kubernetes 1.7引入了聚合层,允许第三方应用程序通过注册为API附加组件来扩展Kubernetes API。
自定义指标API以及聚合层使得像Prometheus这样的监控系统可以向HPA控制器公开特定于应用程序的指标。

hpa 实现了一个控制环,可以周期性的从资源指标API查询特定应用的CPU/MEM信息。

image.png

实战
以下是关于Kubernetes 1.9或更高版本的HPA v2配置的分步指南。您将安装提供核心指标的度量服务器附加组件,
然后您将使用一个演示应用程序来展示基于CPU和内存使用的pod自动伸缩。在指南的第二部分,
您将部署Prometheus和一个自定义API服务器。您将使用聚合器层注册自定义API服务器,然后使用演示应用程序提供的自定义度量配置HPA。

前提

  • go 1.8+
  • clone k8s-prom-hpa repo
cd $GOPATH
git clone https://github.com/stefanprodan/k8s-prom-hpa

安装 Metrics Server

Kubernetes Metrics Server是一个集群范围的资源使用数据聚合器,是Heapster的继承者。
metrics服务器通过从kubernet.summary_api收集数据收集节点和pod的CPU和内存使用情况。
summary API是一个内存有效的API,用于将数据从Kubelet/cAdvisor传递到metrics server。

image.png

如果在v1版本的HPA中,您将需要Heapster提供CPU和内存指标,在HPA v2和Kubernetes 1.8中,
只有度量服务器是需要的,而水平-pod-autoscaler-use-rest-客户机是打开的。
在Kubernetes 1.9中默认启用HPA rest客户端。GKE 1.9附带了预先安装的指标服务器。

kube-system命名空间总部署metrics-server

kubectl create -f ./metrics-server

一分钟后,度量服务器开始报告节点和Pod的CPU和内存使用情况。
查看nodes指标

kubectl get --raw "/apis/metrics.k8s.io/v1beta1/nodes" | jq .

查看pod指标

kubectl get --raw "/apis/metrics.k8s.io/v1beta1/pods" | jq .

基于CPU和内存使用的自动缩放

你将使用一个基于golang的小程序测试hpa.

部署podinfo到默认命名空间

kubectl create -f ./podinfo/podinfo-svc.yaml,./podinfo/podinfo-dep.yaml

http://<K8S_PUBLIC_IP>:31198通过nodeport访问podinfo

接下来定义一个HPA,保持最小两个副本和最大十个如果CPU平均超过80%或如果内存超过200mi。

apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
  name: podinfo
spec:
  scaleTargetRef:
    apiVersion: extensions/v1beta1
    kind: Deployment
    name: podinfo
  minReplicas: 2
  maxReplicas: 10
  metrics:
  - type: Resource
    resource:
      name: cpu
      targetAverageUtilization: 80
  - type: Resource
    resource:
      name: memory
      targetAverageValue: 200Mi

创建HPA

kubectl create -f ./podinfo/podinfo-hpa.yaml

几秒钟之后,HPA控制器与metrics server联系,然后取出CPU和内存使用情况。

kubectl get hpa

NAME      REFERENCE            TARGETS                      MINPODS   MAXPODS   REPLICAS   AGE
podinfo   Deployment/podinfo   2826240 / 200Mi, 15% / 80%   2         10        2          5m

为了提高CPU使用率、运行rakyll/hey进行压力测试

#install hey
go get -u github.com/rakyll/hey

#do 10K requests
hey -n 10000 -q 10 -c 5 http://<K8S_PUBLIC_IP>:31198/

你可以通过以下命令获取HPA event

$ kubectl describe hpa

Events:
  Type    Reason             Age   From                       Message
  ----    ------             ----  ----                       -------
  Normal  SuccessfulRescale  7m    horizontal-pod-autoscaler  New size: 4; reason: cpu resource utilization (percentage of request) above target
  Normal  SuccessfulRescale  3m    horizontal-pod-autoscaler  New size: 8; reason: cpu resource utilization (percentage of request) above target

先将podinfo移除一会儿,稍后将再次部署:

kubectl delete -f ./podinfo/podinfo-hpa.yaml,./podinfo/podinfo-dep.yaml,./podinfo/podinfo-svc.yaml

安装Custom Metrics Server
为了根据custom metrics进行扩展,您需要有两个组件。一个从应用程序中收集指标并将其存储为Prometheus时间序列数据库的组件。
第二个组件将Kubernetes自定义指标API扩展到由收集的k8s-prometheus-adapter提供的指标。

image.png

您将在专用命名空间中部署Prometheus和adapter。

创建monitoring命名空间

kubectl create -f ./namespaces.yaml

将 Prometheus v2部署到monitoring命名空间:
如果您部署到GKE,您可能会得到一个错误:从服务器(禁止)中出错:创建这个错误将帮助您解决这个问题:RBAC on GKE。

kubectl create -f ./prometheus

生成由Prometheus adapter所需的TLS证书:

make certs

部署Prometheus自定义api适配器

kubectl create -f ./custom-metrics-api

列出由prometheus提供的自定义指标:

kubectl get --raw "/apis/custom.metrics.k8s.io/v1beta1" | jq .

获取monitoring命名空间中所有pod的FS信息:

kubectl get --raw "/apis/custom.metrics.k8s.io/v1beta1/namespaces/monitoring/pods/*/fs_usage_bytes" | jq .

基于自定义指标的自动扩容
创建podinfo nodeport服务并在default命名空间中部署:

kubectl create -f ./podinfo/podinfo-svc.yaml,./podinfo/podinfo-dep.yaml

podinfo应用程序的暴露了一个自定义的度量http_requests_total。普罗米修斯适配器删除_total后缀标记度量作为一个计数器度量

从自定义度量API获取每秒的总请求数:

kubectl get --raw "/apis/custom.metrics.k8s.io/v1beta1/namespaces/default/pods/*/http_requests" | jq .
{
  "kind": "MetricValueList",
  "apiVersion": "custom.metrics.k8s.io/v1beta1",
  "metadata": {
    "selfLink": "/apis/custom.metrics.k8s.io/v1beta1/namespaces/default/pods/%2A/http_requests"
  },
  "items": [
    {
      "describedObject": {
        "kind": "Pod",
        "namespace": "default",
        "name": "podinfo-6b86c8ccc9-kv5g9",
        "apiVersion": "/__internal"
      },
      "metricName": "http_requests",
      "timestamp": "2018-01-10T16:49:07Z",
      "value": "901m"
    },
    {
      "describedObject": {
        "kind": "Pod",
        "namespace": "default",
        "name": "podinfo-6b86c8ccc9-nm7bl",
        "apiVersion": "/__internal"
      },
      "metricName": "http_requests",
      "timestamp": "2018-01-10T16:49:07Z",
      "value": "898m"
    }
  ]
}

m代表milli-units,例如,901m意味着milli-requests

创建一个HPA,如果请求数超过每秒10当将扩大podinfo数量:

apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
  name: podinfo
spec:
  scaleTargetRef:
    apiVersion: extensions/v1beta1
    kind: Deployment
    name: podinfo
  minReplicas: 2
  maxReplicas: 10
  metrics:
  - type: Pods
    pods:
      metricName: http_requests
      targetAverageValue: 10

在default命名空间部署podinfo HPA:

kubectl create -f ./podinfo/podinfo-hpa-custom.yaml

过几秒钟HPA从标准的API取得http_requests的值:

kubectl get hpa

NAME      REFERENCE            TARGETS     MINPODS   MAXPODS   REPLICAS   AGE
podinfo   Deployment/podinfo   899m / 10   2         10        2          1m

用25每秒请求数给podinfo服务加压

#install hey
go get -u github.com/rakyll/hey

#do 10K requests rate limited at 25 QPS
hey -n 10000 -q 5 -c 5 http://<K8S-IP>:31198/healthz

几分钟后,HPA开始扩大部署。

kubectl describe hpa

Name:                       podinfo
Namespace:                  default
Reference:                  Deployment/podinfo
Metrics:                    ( current / target )
  "http_requests" on pods:  9059m / 10
Min replicas:               2
Max replicas:               10

Events:
  Type    Reason             Age   From                       Message
  ----    ------             ----  ----                       -------
  Normal  SuccessfulRescale  2m    horizontal-pod-autoscaler  New size: 3; reason: pods metric http_requests above target

以每秒当前的请求速率,部署将永远无法达到10个Pod的最大值。三副本足以让RPS在10每pod.

负载测试结束后,HPA向下扩展部署到初始副本。

Events:
  Type    Reason             Age   From                       Message
  ----    ------             ----  ----                       -------
  Normal  SuccessfulRescale  5m    horizontal-pod-autoscaler  New size: 3; reason: pods metric http_requests above target
  Normal  SuccessfulRescale  21s   horizontal-pod-autoscaler  New size: 2; reason: All metrics below target

你可能已经注意到,自动定标器不使用峰值立即做出反应。默认情况下,指标每30秒同步一次,
并且扩展/收缩当3-5分钟没有重新扩展发生变化时。在这种方式中,HPA防止快速执行并保留了指标生效时间

总结

不是所有的系统都可以依靠CPU/内存使用指标单独满足SLA,大多数Web和移动后端需要以每秒请求处理任何突发流量进行自动缩放。
对于ETL应用程序,可能会由于作业队列长度超过某个阈值而触发自动缩放,等等。
通过prometheus检测你应用程序的正确指,并为自动是很所提供正确指标,您可以微调您的应用程序更好地处理突发和确保高可用性。

参考

https://github.com/kubernetes/metrics

https://github.com/kubernetes-incubator/custom-metrics-apiserver

https://github.com/kubernetes-incubator/metrics-server

https://kubernetes.io/docs/tasks/debug-application-cluster/core-metrics-pipeline/

https://github.com/kubernetes/community/blob/master/contributors/design-proposals/instrumentation/resource-metrics-api.md

https://github.com/kubernetes/community/blob/master/contributors/design-proposals/instrumentation/metrics-server.md

https://github.com/stefanprodan/k8s-prom-hpa

https://github.com/DirectXMan12/k8s-prometheus-adapter

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 200,841评论 5 472
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 84,415评论 2 377
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 147,904评论 0 333
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,051评论 1 272
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,055评论 5 363
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,255评论 1 278
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,729评论 3 393
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,377评论 0 255
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,517评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,420评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,467评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,144评论 3 317
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,735评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,812评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,029评论 1 256
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,528评论 2 346
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,126评论 2 341

推荐阅读更多精彩内容