k8s--HPA 控制器

简介: k8s--HPA 控制器

Horizontal Pod Autoscaler(HPA) 控制器介绍


在前面的学习中,我们已经可以实现通过手工执行 kubectl scale 命令实现 pod 扩容或缩容,但是这显示不符合 kubernetes 的定位目标--自动化、智能化。kubernetes 期望可以实现通过监测 pod 的使用情况,实现 pod 数量的自动调整,于是就产生了 Horizontal Pod AutoScaler(HPA)这种控制器

HPA 可以获取每个 Pod 的利用率,然后和 HPA 中定义的指标进行对比,同时计算出需要伸缩的具体值,最后实现 pod 数量的调整,其实 HPA 于之前的 Deployment 一样,也属于 kubernetes 资源对象,它通过追踪分析 RC 控制的所有目标 Pod 的负载变化情况,来确定是否需要针对性的调整目标 pod 的副本数,这是 HPA 的实现原理。

Pod 水平自动扩缩(Horizontal Pod Autoscaler) 可以基于 CPU 利用率自动扩缩 ReplicationController、Deployment、ReplicaSet 和 StatefulSet 中的 Pod 数量。 除了 CPU 利用率,也可以基于其他应程序提供的自定义度量指标来执行自动扩缩。 Pod 自动扩缩不适用于无法扩缩的对象,比如 DaemonSet

HPA Controller 会通过调整副本数量使得 CPU 使用率尽量向期望值靠近,而且不是完全相等.另外,官方考虑到自动扩展的决策可能需要一段时间才会生效:例如当 pod 所需要的 CPU 负荷过大,从而在创建一个新 pod 的过程中,系统的 CPU 使用量可能会同样在有一个攀升的过程。所以,在每一次作出决策后的一段时间内,将不再进行扩展决策。对于扩容而言,这个时间段为 3 分钟,缩容为 5 分钟(可以通过 --horizontal-pod-autoscaler-downscale-delay, --horizontal-pod-autoscaler-upscale-delay 进行调整)

HPA 的 API 有三个版本,通过 kubectl api-versions | grep autoscal 可看到

[root@dce-10-6-215-215 ~]# kubectl api-versions | grep autoscal
autoscaling/v1
autoscaling/v2beta1
autoscaling/v2beta2

查看使用的版本:

[root@dce-10-6-215-215 ~]# kubectl explain hpa
KIND:     HorizontalPodAutoscaler
VERSION:  autoscaling/v1  # 可以看到目前使用的是这个版本
DESCRIPTION:
     configuration of a horizontal pod autoscaler.
FIELDS:
   apiVersion <string>
......

查看其他指定的版本

# 查看 autoscaling/v2beta1 的版本
[root@dce-10-6-215-215 ~]# kubectl explain hpa --api-version=autoscaling/v2beta1
KIND:     HorizontalPodAutoscaler
VERSION:  autoscaling/v2beta1
DESCRIPTION:
     HorizontalPodAutoscaler is the configuration for a horizontal pod
     autoscaler, which automatically manages the replica count of any resource
     implementing the scale subresource based on the metrics specified.
FIELDS:
   apiVersion <string>

三个版本之前的区别如下

  • autoscaling/v1:只支持基于CPU指标的缩放;
  • autoscaling/v2beta1:支持 Resource Metrics(资源指标,如 pod 内存)和 Custom Metrics(自定义指标)的缩放;
  • autoscaling/v2beta2:支持 Resource Metrics(资源指标,如 pod 的内存)和 Custom Metrics(自定义指标)和 ExternalMetrics


手动扩缩容


pc-deployment.yaml 文件内容如下

查看代码

 apiVersion: apps/v1
kind: Deployment # 类型为 deployment
metadata:
  name: pc-deployment # deployment 的名称
  namespace: test
spec:
  replicas: 4 # 副本数为 3
  selector:  # 选择器,和 template 的对应
    matchLabels:
      app: nginx-pod
  template:
    metadata:
      labels:
        app: nginx-pod
    spec:
      containers:
      - name: nginx
        image: nginx:1.14

现在我们是有一个 deployment 和三个 pod,如下

[root@dce-10-6-215-215 ~]# kubectl get deploy,pod -n test
NAME                            READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/pc-deployment   3/3     3            3           15s
NAME                                 READY   STATUS    RESTARTS   AGE
pod/pc-deployment-5db6b86685-2b8rs   1/1     Running   0          15s
pod/pc-deployment-5db6b86685-2mv2n   1/1     Running   0          15s
pod/pc-deployment-5db6b86685-5gnjx   1/1     Running   0          15s

第一种方式:我们可以更改 yaml 文件,vim 编辑修改 yaml 文件,改好副本数保存后,在 apply 一下,我这里把副本数改为了 4

# 修改副本数,改为 4
[root@dce-10-6-215-215 ~]# vim pc-deployment.yaml
# 修改完文件后重新配置一下
[root@dce-10-6-215-215 ~]# kubectl apply -f pc-deployment.yaml
deployment.apps/pc-deployment configured
# 查看发现有 1 个 pod 正在创建
[root@dce-10-6-215-215 tmp]# kubectl get pod -n test
NAME                             READY   STATUS              RESTARTS   AGE
pc-deployment-5db6b86685-2b8rs   1/1     Running             0          3m45s
pc-deployment-5db6b86685-2mv2n   1/1     Running             0          3m45s
pc-deployment-5db6b86685-5gnjx   1/1     Running             0          3m45s
pc-deployment-5db6b86685-x6t4p   1/1     ContainerCreating   0          14s
# 4 个 pod 都已经运行了
[root@dce-10-6-215-215 ~]# kubectl get pod -n test
NAME                             READY   STATUS    RESTARTS   AGE
pc-deployment-5db6b86685-2b8rs   1/1     Running   0          3m47s
pc-deployment-5db6b86685-2mv2n   1/1     Running   0          3m47s
pc-deployment-5db6b86685-5gnjx   1/1     Running   0          3m47s
pc-deployment-5db6b86685-x6t4p   1/1     Running   0          16s

第二种方式:可以通过编辑 deployment 的副本数量,修改 spec:replicas: 5 即可

# 通过 edit 实现,改完文件保存之后就会自动生效
[root@dce-10-6-215-215 ~]# kubectl edit deploy pc-deployment -n test
deployment.apps/pc-deployment edited
# 查看 pod 的数量,变成了 6 个 pod
[root@dce-10-6-215-215 ~]# kubectl get pod,deploy -n test
NAME                                 READY   STATUS    RESTARTS   AGE
pod/pc-deployment-5db6b86685-2b8rs   1/1     Running   0          8m50s
pod/pc-deployment-5db6b86685-2mv2n   1/1     Running   0          8m50s
pod/pc-deployment-5db6b86685-5gnjx   1/1     Running   0          8m50s
pod/pc-deployment-5db6b86685-hn7zz   1/1     Running   0          64s
pod/pc-deployment-5db6b86685-x6t4p   1/1     Running   0          5m19s
NAME                            READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/pc-deployment   5/5     5            5           8m50s

第三种方式:使用命令的方式

# 变更副本数为 6 个,注意,扩缩的时候写的是控制器的名称,不是 pod
[root@dce-10-6-215-215 ~]# kubectl scale deploy pc-deployment --replicas=6 -n test
deployment.apps/pc-deployment scaled
# 查看 deployment
[root@dce-10-6-215-215 ~]# kubectl get deploy pc-deployment -n test
NAME            READY   UP-TO-DATE   AVAILABLE   AGE
pc-deployment   6/6     6            6           15m
# 查看 pod
[root@dce-10-6-215-215 ~]# kubectl get pod -n test
NAME                             READY   STATUS    RESTARTS   AGE
pc-deployment-5db6b86685-2b8rs   1/1     Running   0          15m
pc-deployment-5db6b86685-2mv2n   1/1     Running   0          15m
pc-deployment-5db6b86685-5gnjx   1/1     Running   0          15m
pc-deployment-5db6b86685-dzrxj   1/1     Running   0          2m48s
pc-deployment-5db6b86685-hn7zz   1/1     Running   0          8m7s
pc-deployment-5db6b86685-x6t4p   1/1     Running   0          12m


HPA 实现自动扩缩容


在使用 HPA 的时候需要先部署一下 metrics-server,收集集群资源利用率

官网:https://github.com/kubernetes-sigs/metrics-server/releases

你也可以通过下面的命令进行安装

kubectl apply -f https://github.com/kubernetes-sigs/metrics-server/releases/download/v0.6.1/components.yaml

安装完成之后等会执行 kubectl top node,可以看到下面的输出就没问题

[root@dce-10-6-215-215 ~]# kubectl top nodes
NAME               CPU(cores)   CPU%   MEMORY(bytes)   MEMORY%
dce-10-6-215-190   464m         6%     2302Mi          15%
dce-10-6-215-200   620m         4%     2397Mi          7%
dce-10-6-215-215   3305m        44%    10574Mi         69%

目前是有 6 个 pod,如下

[root@dce-10-6-215-215 ~]# kubectl get pod,deploy -n test
NAME                                 READY   STATUS    RESTARTS   AGE
pod/pc-deployment-5db6b86685-2b8rs   1/1     Running   0          105m
pod/pc-deployment-5db6b86685-2mv2n   1/1     Running   0          105m
pod/pc-deployment-5db6b86685-5gnjx   1/1     Running   0          105m
pod/pc-deployment-5db6b86685-dzrxj   1/1     Running   0          92m
pod/pc-deployment-5db6b86685-hn7zz   1/1     Running   0          98m
pod/pc-deployment-5db6b86685-x6t4p   1/1     Running   0          102m
NAME                            READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/pc-deployment   6/6     6            6           105m

创建一个 deploy-hpa.yaml 文件,如下

apiVersion: autoscaling/v1   # 版本为 autoscaling/v1
kind: HorizontalPodAutoscaler  # 类型为 HPA
metadata:
  namespace: test  # namespace
  name: nginx-app1-podautoscaler # HPA 的名称
  labels:
    app: nginx-pod  # 选择 app=nginx-pod 的 pod
spec:
  scaleTargetRef:  # 要伸缩的目标资源,这里为 deployment
    apiVersion: apps/v1 # 伸缩类型的版本,这里为 deployment,版本为 apps/v1
    kind: Deployment  # 扩缩容的对象是 deployment
    name: pc-deployment # deployment 的名称
  minReplicas: 2  # 最小副本数
  maxReplicas: 20 # 最大副本数
  targetCPUUtilizationPercentage: 20  # 定义检测的 CPU 使用率指标的阈值,这里为 20,当小于 20% 的时候就会缩容,大于的时候就会扩容

在来创建一下 HPA 控制器

[root@dce-10-6-215-215 ~]# kubectl apply -f deploy-hpa.yaml
horizontalpodautoscaler.autoscaling/nginx-app1-podautoscaler created

查看 HPA 控制器

# TARGETS / 左边的为 cpu 使用率,右边的为我们设置的阈值
# MINPODS 最小的 pod 数,MAXPODS 最大的 pod 数,当前的副本数 REPLICAS
[root@dce-10-6-215-215 ~]# kubectl get hpa -n test
NAME                       REFERENCE                  TARGETS   MINPODS   MAXPODS   REPLICAS   AGE
nginx-app1-podautoscaler   Deployment/pc-deployment   0%/20%    2         20        6          30s

查看 HPA 的详细信息

[root@dce-10-6-215-215 ~]# kubectl describe hpa nginx-app1-podautoscaler -n test
Name:                                                  nginx-app1-podautoscaler
Namespace:                                             test
Labels:                                                app=nginx-pod
Annotations:                                           CreationTimestamp:  Sun, 10 Jul 2022 12:40:01 +0800
Reference:                                             Deployment/pc-deployment
Metrics:                                               ( current / target )
  resource cpu on pods  (as a percentage of request):  0% (0) / 20%
Min replicas:                                          2
Max replicas:                                          20
Deployment pods:                                       6 current / 6 desired
Conditions:
  Type            Status  Reason               Message
  ----            ------  ------               -------
  AbleToScale     True    ScaleDownStabilized  recent recommendations were higher than current one, applying the highest recent recommendation
  ScalingActive   True    ValidMetricFound     the HPA was able to successfully calculate a replica count from cpu resource utilization (percentage of request)
  ScalingLimited  False   DesiredWithinRange   the desired count is within the acceptable range

等 5 分钟后在去查看 pod 和 hpa

# 查看 HPA
[root@dce-10-6-215-215 ~]# kubectl get hpa -n test
NAME                       REFERENCE                  TARGETS   MINPODS   MAXPODS   REPLICAS   AGE
nginx-app1-podautoscaler   Deployment/pc-deployment   0%/20%    2         20        2          8m22s
# 查看 pod,发现只有 2 个 pod 了,这是因为 cpu 内存占用一直很小,所以 HPA 将 pod 数量改为了 2 ,因为我们写的最小的 pod 数量为 2
[root@dce-10-6-215-215 ~]# kubectl get pod,deploy -n test
NAME                                 READY   STATUS    RESTARTS   AGE
pod/pc-deployment-5db6b86685-2b8rs   1/1     Running   0          117m
pod/pc-deployment-5db6b86685-2mv2n   1/1     Running   0          117m
NAME                            READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/pc-deployment   2/2     2            2           117m

在来查看 HPA 的详情

[root@dce-10-6-215-215 ~]# kubectl describe hpa nginx-app1-podautoscaler -n test
Name:                                                  nginx-app1-podautoscaler
Namespace:                                             test
Labels:                                                app=nginx-pod
Annotations:                                           CreationTimestamp:  Sun, 10 Jul 2022 12:40:01 +0800
Reference:                                             Deployment/pc-deployment
Metrics:                                               ( current / target )
  resource cpu on pods  (as a percentage of request):  0% (0) / 20%
Min replicas:                                          2
Max replicas:                                          20
Deployment pods:                                       2 current / 2 desired
Conditions:
  Type            Status  Reason            Message
  ----            ------  ------            -------
  AbleToScale     True    ReadyForNewScale  recommended size matches current size
  ScalingActive   True    ValidMetricFound  the HPA was able to successfully calculate a replica count from cpu resource utilization (percentage of request)
  ScalingLimited  True    TooFewReplicas    the desired replica count is less than the minimum replica count
Events:
  Type    Reason             Age   From                       Message
  ----    ------             ----  ----                       -------
    # 可以看到这里进行了缩容
  Normal  SuccessfulRescale  11m   horizontal-pod-autoscaler  New size: 2; reason: All metrics below target


基于 cpu 和 内存的限制


apiVersion: autoscaling/v2beta1  # 版本为 autoscaling/v2beta1,autoscaling/v1 只有 cpu
kind: HorizontalPodAutoscaler  # 类型为 HPA
metadata:
  namespace: test  # namespace
  name: nginx-app1-podautoscaler # HPA 的名称
  labels:
    app: nginx-pod  # 选择 app=nginx-pod 的 pod
spec:
  scaleTargetRef: # 要伸缩的目标资源,这里为 deployment
    apiVersion: apps/v1  # 伸缩类型的版本,这里为 deployment,版本为 apps/v1
    kind: Deployment  # 扩缩容的对象是 deployment
    name: pc-deployment # deployment 的名称
  minReplicas: 2  # 最小副本数
  maxReplicas: 20 # 最大副本数
  metrics:
  - type: Resource
    resource:
      name: cpu  # 限制 cpu
      targetAverageUtilization: 80 # 阈值为 80
  - type: Resource
    resource:
      name: memory  # 限制内存
      targetAverageValue: 30Mi # 阈值为 30m

如上,设置了 pc-deployment 的 deployment 控制的 pod 的 HPA 限制,当 cpu 使用超过设置的 80%,内存使用超过 30Mi 时就触发自动扩容,副本数最小为 2,最大为20。


删除 hpa 控制器


[root@dce-10-6-215-215 ~]# kubectl delete -f deploy-hpa.yaml
horizontalpodautoscaler.autoscaling "nginx-app1-podautoscaler" deleted

相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
7月前
|
Kubernetes Cloud Native 应用服务中间件
云原生|kubernetes|ResourceQuota 资源与准入控制器
云原生|kubernetes|ResourceQuota 资源与准入控制器
120 0
|
1月前
|
Kubernetes 监控 调度
【赵渝强老师】K8s的DaemonSet控制器
DaemonSet控制器确保每个节点上运行一个Pod副本,适用于监控、日志收集等场景。通过示例创建DaemonSet并查看Pod信息,展示了其自动扩展和回收的能力。视频讲解和代码示例详细说明了DaemonSet的使用方法和调度机制。
|
1月前
|
Kubernetes 调度 容器
【赵渝强老师】K8s中Job控制器单工作队列的串行方式
Kubernetes中的Job控制器用于管理一次性任务,确保任务完成后不再重启。本文介绍了Job的工作原理、运行方式及示例,包括创建Job、查看Job和Pod信息等步骤,并附有视频讲解。
|
1月前
|
Kubernetes 双11 容器
【赵渝强老师】Kubernetes中的控制器
Kubernetes通过控制器管理Pod的生命周期,以应对不同场景需求,如Deployment、DaemonSet、Job等。控制器可自动调整Pod数量和重启故障Pod,确保系统稳定运行。视频讲解和详细内容见下文。
|
1月前
|
Kubernetes 应用服务中间件 nginx
【赵渝强老师】K8s中的Deployment控制器
Kubernetes中的Deployment用于部署无状态应用程序,管理Pod的数量、更新方式和资源限制。通过创建和管理ReplicaSet,Deployment可以实现Pod的自动扩缩容、滚动更新和回滚。本文介绍了Deployment的基本概念,并通过一个具体的示例演示了如何使用Deployment创建、更新和管理Pod。
|
1月前
|
存储 Kubernetes 调度
【赵渝强老师】K8s中Deployment控制器与StatefulSet控制器的区别
K8s中的Deployment控制器用于管理无状态应用程序,关注Pod数量、更新方式等;而StatefulSets控制器则管理有状态应用程序,提供持久存储和唯一标识符,适用于需要稳定网络标识符和持久化存储的场景。两者的主要区别在于是否维护状态和顺序。
|
1月前
|
存储 Kubernetes 调度
【赵渝强老师】K8s的有状态控制器StatefulSet
在Kubernetes中,StatefulSets用于部署有状态应用程序,提供持久存储和唯一标识符。与Deployment不同,StatefulSets确保Pod的标识符在重新调度后保持不变,适用于需要稳定网络标识符和持久存储的场景。本文介绍了StatefulSets的创建、扩容与缩容、更新与回滚等操作,并提供了具体示例和视频讲解。
|
1月前
|
Kubernetes Linux 调度
【赵渝强老师】K8s的周期性任务控制器CronJob
本文介绍了K8s中的CronJob控制器,它类似于Linux的crontab命令,用于管理和调度定时作业。CronJob可以设置在未来某一时间运行作业一次或在指定时间点重复运行作业。文章通过一个示例展示了如何创建和使用CronJob控制器,包括创建配置文件、应用配置、查看Pod信息和日志等步骤。同时,还解释了CronJob的时间表示方式及其限制。
|
1月前
|
Kubernetes 调度 容器
【赵渝强老师】K8s的Job控制器多工作队列的并行方式
Kubernetes Job 是一次性任务控制器,用于控制 Pod 中的容器执行特定任务。本文介绍了 Job 控制器的工作原理、运行方式及多工作队列并行执行的示例。示例中创建了 5 个作业,以 3 个队列并行执行,整个过程需 2 分钟。文中还提供了详细的 YAML 文件配置和执行命令。
|
7月前
|
运维 Kubernetes 监控
Kubernetes详解(十九)——Kubernetes Pod控制器
Kubernetes详解(十九)——Kubernetes Pod控制器
104 3