Kubernetes Autoscaler解析

本文涉及的产品
公共DNS(含HTTPDNS解析),每月1000万次HTTP解析
容器服务 Serverless 版 ACK Serverless,317元额度 多规格
全局流量管理 GTM,标准版 1个月
简介: 随着Kubernetes生态的不断壮大,一度被誉为新一代数据中心操作系统(DCOS),从资源角度来讲,K8S其核心工作也是管理整个集群的计算资源,并按需合理分配给系统里的程序(以Pod为基础的各种WorkLoad)。本质也是解决资源与业务负载之间供需平衡的问题。因此,了解Kubernetes自动扩展功能的相关原理,可以帮助我们在资源管理层面获得更多的价值,有利于提升运维效能。

      随着Kubernetes生态的不断壮大,一度被誉为新一代数据中心操作系统(DCOS),从资源角度来讲,K8S其核心工作也是管理整个集群的计算资源,并按需合理分配给系统里的程序(以Pod为基础的各种WorkLoad)。本质也是解决资源与业务负载之间供需平衡的问题。因此,了解Kubernetes自动扩展功能的相关原理,可以帮助我们在资源管理层面获得更多的价值,有利于提升运维效能。  

伸缩对象?

       在Kubernetes生态环境中,通常有两件关键事项需要进行弹性伸缩,以使得资源处于最优状态:

       Pod:对于给定的应用程序,假设我们正在运行X副本,如果发出的请求超出X Pod池的处理能力,则为该应用程序扩展到多个X副本是一个好主意。为了使它无缝运行,我们的节点应具有足够的可用资源,以便可以成功调度和执行这些额外的Pod。这使我们进入了扩展规模的第二部分。

      Node:所有节点的总容量代表集群的容量。如果工作负载需求超出了此容量,则必须将节点添加到集群中,并确保可以有效地计划和执行工作负载。如果Pod继续扩展,则有时节点可用的资源将耗尽,我们将不得不添加更多节点以增加集群级别的整体可用资源。

伸缩时机?

      何时扩缩的决定包括两个部分:一个是连续测量某个指标,而该指标何时超过阈值,然后通过缩放特定资源对其进行操作。例如,我们可能想要测量我们的Pod的平均CPU消耗,然后在CPU消耗超过80%时触发定标操作。但是一个度量标准并不适合所有用例,对于不同类型的应用程序,该度量标准可能会有所不同。例如,对于消息队列,处于等待状态的消息数可能是适当的指标。对于内存密集型应用程序,内存消耗可能是该指标。如果我们有一个业务应用程序,对于给定的容量Pod,每秒处理大约1000个事务,那么我们可能要使用该指标并在Pod中的TPS达到850以上时进行扩展。

      到目前为止,我们仅考虑了扩展部分,但是当工作负载使用率下降时,应该有一种方法可以适当地进行扩展,而不会引起正在处理的现有请求的中断。我们将在后面的部分中查看这些事情的实现细节。

如何伸缩

      对于Pod而言,只需在复制控制器中更改副本数即可。对于节点,若基于云平台,我们可以调用云提供商的API,创建一个新实例,并使它成为群集的一部分,只不过相对平常的操作,可能会花费更多时间。

Kubernetes弹性伸缩

      了解了弹性伸缩后,让我们讨论Kubernetes弹性伸缩的特定实现和技术细节。

       1、Cluster Autoscaler

      集群自动扩缩器在Kubernetes中用于动态扩展集群(即节点)。它会持续监视Pod,如果发现Pod无法安排,则根据Pod Condition,选择扩展。这比查看节点的CPU总百分比要有效得多。由于创建节点最多可能需要一分钟或更长时间,具体取决于我们的云提供商和其他因素,因此可能需要一些时间才能安排Pod。在集群中,我们可能有多个节点池,例如,一个用于计费应用程序的节点池和另一个用于机器学习工作负载的节点池。此外,节点可以分布在区域中的各个可用区中,并且扩展方式可能会因拓扑而异。集群自动扩缩器提供各种标记和方法来调整节点扩缩行为。

      为了缩减规模,需要查看该节点上的平均利用率,当然也可以依据其他因素。例如,如果具有节点中断预算的节点在无法重新调度的节点上运行,则无法从群集中剔除该节点。集群自动扩缩器提供了一种方法,可以优雅地终止节点,并且最多可以有10分钟的时间来移动Pod。

       2、Horizontal Pod Autoscaler (HPA)

      Pod水平自动扩缩器是一个控制回路,可监视和扩缩部署中的Pod。由控制器管理器的 --horizontal-pod-autoscaler-sync-period 参数指定周期(默认值为 15 秒)。每个周期内,控制管理器根据每个 HorizontalPodAutoscaler 定义中指定的指标查询资源利用率。控制管理器可以从资源度量指标 API(按 Pod 统计的资源用量)和自定义度量指标 API(其他指标)获取度量值。我们可以定义阈值以及部署应扩展到的最小和最大扩展。HPA的原始版本为GA(autoscaling / v1),仅支持将CPU作为可以监控的指标。Beta版的当前HPA版本(autoscaling / v2beta1)支持内存和其他自定义指标。我们来看下Pod 水平自动扩缩工作机制,如下图所示:

      通常情况下,控制器将从一系列的聚合 API(metrics.k8s.io、custom.metrics.k8s.io 和 external.metrics.k8s.io)中获取度量值。创建HPA对象并能够查询该Pod的指标后,我们可以看到相关详细信息:


[administrator@JavaLangOutOfMemory k8s-master %]kubectl get hpa NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE helloetst-ownay28d Deployment/helloetst-ownay28d 8% / 60% 1 4 1 23h

     我们可以通过向控制管理器添加标志来对水平pod自动缩放器的行为进行一些调整:

      1、通过使用标志-horizontal-pod-autoscaler-sync-periodon控制管理器,确定hPa监视Pod池上给定指标的频率。默认同步周期为30秒。

      2、两次操作之间的延迟默认为3分钟,可以使用标志-horizontal-pod-autoscaler-upscale-delay进行控制。

      3、两次缩减操作之间的延迟默认情况下为5分钟,并且可以通过标志-horizontal-pod-autoscaler-downscale-delay进行调整。

      关于指标, 在Kubernetes 1.9及更高版本中,API指标服务器是首选方法。

伸缩策略

      从 v1.18 开始,v2beta2 API 允许通过 HPA 的 behavior 字段配置扩缩行为。在 behavior 字段中的 scaleUp 和 scaleDown 分别指定扩容和缩容行为。可以两个方向指定一个稳定窗口,以防止扩缩目标中副本数量的波动。类似地,指定扩缩策略可以控制扩缩时副本数的变化率。我们看一个关于默认的Demo行为,具体如下所示:


behavior:
  scaleDown:
    stabilizationWindowSeconds: 300
    policies:
    - type: Percent
      value: 100
      periodSeconds: 15
  scaleUp:
    stabilizationWindowSeconds: 0
    policies:
    - type: Percent
      value: 100
      periodSeconds: 15
    - type: Pods
      value: 4
      periodSeconds: 15
    selectPolicy: Max

      用于缩小稳定窗口的时间为 300 秒(或是 --horizontal-pod-autoscaler-downscale-stabilization 参数设定值)。只有一种缩容的策略,允许 100% 删除当前运行的副本,这意味着扩缩目标可以缩小到允许的最小副本数。对于扩容,没有稳定窗口。当指标显示目标应该扩容时,目标会立即扩容。这里有两种策略:每 15 秒添加 4 个 Pod 或 100% 当前运行的副本数,直到 HPA 达到稳定状态。其他的策略可参考官网定义。

伸缩算法

      从最基本的角度来看,Pod 水平自动扩缩控制器根据当前指标和期望指标来计算扩缩比例。具体可参考:


期望副本数 = ceil[当前副本数 * (当前指标 / 期望指标)]

     举个简单的场景:假设当前度量值为 200m,目标设定值为 100m,那么根据公式 200.0/100.0 =2.0, 副本数量将会翻倍。如果当前指标为 50m,副本数量将会减半,因为50.0/100.0 = 0.5。如果计算出的扩缩比例接近 1.0 (根据--horizontal-pod-autoscaler-tolerance 参数全局配置的容忍值,默认为 0.1),将会放弃本次扩缩。

      针对如下异常场景,算法策略如下:

      1、如果 HorizontalPodAutoscaler 指定的是 targetAverageValue 或targetAverage

Utilization, 那么将会把指定 Pod 度量值的平值做为 currentMetricValue。 然而,在检查容忍度和决定最终扩缩值前,我们仍然会把那些无法获取指标的 Pod 统计进去。

     2、所有被标记了删除时间戳(Pod 正在关闭过程中)的 Pod 和失败的 Pod 都会被忽略。

      3、如果某个 Pod 缺失度量值,它将会被搁置,只在最终确定扩缩数量时再考虑。

      4、当使用 CPU 指标来扩缩时,任何还未就绪(例如还在初始化)状态的 Pod 或 最近的指标 度量值采集于就绪状态前的 Pod,该 Pod 也会被搁置。

      5、由于受技术限制,Pod 水平扩缩控制器无法准确的知道 Pod 什么时候就绪, 也就无法决定是否暂时搁置该 Pod。--horizontal-pod-autoscaler-initial-readiness-delay 参数(默认为 30s)用于设置 Pod 准备时间, 在此时间内的 Pod 统统被认为未就绪。--horizontal-pod-autoscaler-cpu-initialization-period 参数(默认为5分钟) 用于设置 Pod 的初始化时间, 在此时间内的 Pod,CPU 资源度量值将不会被采纳。

      最后,来一张简单的思维导图,可以帮助大家能够深入去了解、学习K8S的弹性伸缩机制以及其所涉及的关键要素。

相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
3月前
|
Kubernetes API 调度
Kubernetes 架构解析:理解其核心组件
【8月更文第29天】Kubernetes(简称 K8s)是一个开源的容器编排系统,用于自动化部署、扩展和管理容器化应用。它提供了一个可移植、可扩展的环境来运行分布式系统。本文将深入探讨 Kubernetes 的架构设计,包括其核心组件如何协同工作以实现这些功能。
323 0
|
10天前
|
运维 Kubernetes Cloud Native
Kubernetes云原生架构深度解析与实践指南####
本文深入探讨了Kubernetes作为领先的云原生应用编排平台,其设计理念、核心组件及高级特性。通过剖析Kubernetes的工作原理,结合具体案例分析,为读者呈现如何在实际项目中高效部署、管理和扩展容器化应用的策略与技巧。文章还涵盖了服务发现、负载均衡、配置管理、自动化伸缩等关键议题,旨在帮助开发者和运维人员掌握利用Kubernetes构建健壮、可伸缩的云原生生态系统的能力。 ####
|
8天前
|
存储 Kubernetes 调度
深度解析Kubernetes中的Pod生命周期管理
深度解析Kubernetes中的Pod生命周期管理
|
25天前
|
存储 Kubernetes 监控
深度解析Kubernetes在微服务架构中的应用与优化
【10月更文挑战第18天】深度解析Kubernetes在微服务架构中的应用与优化
94 0
|
3月前
|
Kubernetes Cloud Native API
自动扩缩容:Kubernetes Autoscaler的神奇魔法,让你的应用在云海中遨游!
【8月更文挑战第8天】在云原生环境中,容器化与微服务架构普及的同时,应用管理复杂度也随之提升。自动扩缩容作为解决资源动态调整的关键技术,可根据负载变化自动增减资源,从而优化成本和性能。本文以Kubernetes为例,介绍其Autoscaler组件如HPA如何基于CPU使用率等指标自动调整Pod数量,并探讨如何利用自定义指标实现更灵活的自动扩缩容策略,以满足现代应用的弹性需求。
155 9
|
4月前
|
Kubernetes 负载均衡 Cloud Native
Kubernetes经典理论与核心概念解析
Kubernetes经典理论与核心概念解析
|
4月前
|
运维 Kubernetes Docker
|
5月前
|
Kubernetes 应用服务中间件 API
Kubernetes关键组件解析
【6月更文挑战第12天】Kubernetes是一个用于管理容器集群的平台,由Master节点负责集群控制,而Node节点执行管理命令。
|
3天前
|
监控 Java 应用服务中间件
高级java面试---spring.factories文件的解析源码API机制
【11月更文挑战第20天】Spring Boot是一个用于快速构建基于Spring框架的应用程序的开源框架。它通过自动配置、起步依赖和内嵌服务器等特性,极大地简化了Spring应用的开发和部署过程。本文将深入探讨Spring Boot的背景历史、业务场景、功能点以及底层原理,并通过Java代码手写模拟Spring Boot的启动过程,特别是spring.factories文件的解析源码API机制。
16 2
|
1月前
|
缓存 Java 程序员
Map - LinkedHashSet&Map源码解析
Map - LinkedHashSet&Map源码解析
67 0