Azure Kubernetes 服务中的群集自动缩放概述

若要满足 Azure Kubernetes 服务 (AKS) 中的应用程序需求,可能需要调整运行工作负载的节点数。 集群自动扩缩容组件会监视集群中因资源限制而无法调度的 Pod。 当集群自动扩缩器检测到未调度的 Pod 时,它会增加节点池中的节点数量,以满足应用程序需求。 它还会定期检查没有任何已安排的 Pod 的节点,并根据需要缩减节点数。

本文介绍群集自动缩放程序在 AKS 中的工作原理。 此外,还提供了为 AKS 工作负载配置群集自动缩放程序时的指导、最佳做法和注意事项。 若要为 AKS 工作负载启用、禁用或更新群集自动缩放程序,请参阅在 AKS 中使用群集自动缩放程序

关于集群自动扩缩器

群集通常需要一种自动缩放方式以适应不断变化的应用程序需求(例如,工作日与夜间或周末之间)。 可以通过以下方式缩放 AKS 群集:

  • 集群自动扩缩器会定期检查由于资源限制而无法调度到节点上的 Pod。 群集随后会自动增加节点数。 使用群集自动缩放程序时,会禁用手动缩放。 有关详细信息,请参阅纵向扩展的工作原理
  • 水平 Pod 自动缩放程序会在 Kubernetes 群集中使用指标服务器来监视 Pod 的资源需求。 如果应用程序需要更多资源,则会自动增加 Pod 数以满足需求。

显示群集自动缩放程序和水平 Pod 自动缩放程序通常如何协同工作以支持所需的应用程序需求的屏幕截图。

常见做法是为节点启用群集自动缩放程序,并为 Pod 启用垂直 Pod 自动缩放程序或水平 Pod 自动缩放程序。 启用群集自动缩放程序后,当节点池大小低于最小节点计数时(上限为最大节点计数),它会应用指定的缩放规则。 群集自动缩放程序会等待生效,直到节点池中需要新节点或可从当前节点池中安全删除某个节点为止。 有关详细信息,请参阅纵向缩减的工作原理

最佳做法和注意事项

  • 使用群集自动缩放程序实现可用性区域时,请为每个区域使用单个节点池。 将参数 --balance-similar-node-groups 设置为 True,以便在扩容操作期间保持您的工作负载跨可用区的节点均衡分布。 如果不使用此方法,纵向缩减操作可能会中断跨区域的节点平衡。 对于多区域节点池,还可以使用 自动区域放置(--zones auto让 AKS 动态选取区域,从而将节点置于具有容量的区域,同时应用每个区域的最大实例百分比为 50%。 创建节点池或更新现有节点池时,可以使用自动区域放置。

注释

群集自动缩放程序不具有区域感知性,并且区域分配由基础虚拟机规模集处理。 使用基于区域的 Pod 拓扑调度策略 在单个多区域节点池上时,上述最佳做法变得更加重要,因为限制性约束可能会使 Pod 处于挂起状态,尤其是在容量受限的区域或区域故障情境中。

  • 对于具有超过 400 个节点的群集,建议使用 Azure CNI 或 Azure CNI Overlay

  • 若要 在现成节点池和按需节点池上同时有效运行工作负荷,请考虑使用 优先级扩展器。 此方法允许根据分配的优先级横向扩展节点池。 以下配置说明了此设置。

    apiVersion: v1
    kind: ConfigMap
    metadata:
      name: cluster-autoscaler-priority-expander
      namespace: kube-system
    data:
      priorities: |-
        10: 
          - .*spotpool1.*
          - .*spotpool2.*
        50: 
          - .*ondemandpool1.*
    
  • 在 Pod 上分配 CPU/内存请求时,请谨慎行事。 集群自动扩缩器是根据处于 Pending 状态的 Pod 进行横向扩容,而不是根据节点的 CPU/内存压力。

  • 对于 同时托管长时间运行的工作负荷(例如 Web 应用)和短作业工作负荷或突发作业工作负荷的群集,请使用 地缘规则扩展器将它们分成不同的节点池。

  • 使用 PodDisruptionBudget 来帮助防止不必要的节点耗尽或缩减操作。 在 Pod 规范中指定注解 cluster-autoscaler.kubernetes.io/safe-to-evict: "false" 也会防止这些 Pod 被驱逐。 请谨慎使用此批注,因为它可能会导致群集自动缩放程序在耗尽包含此批注的正在运行的 Pod 的节点时遇到问题。

  • 在启用了自动缩放程序的节点池中,通过删除工作负荷来缩减节点,而不是手动减少节点池的最小/最大计数。 如果节点池已达到最大容量,或者节点上正在运行活动工作负载,这可能会出现问题,可能会导致群集自动缩放程序出现意外行为。

  • 如果 Pod 的 PriorityClass 值低于 -10,则节点不会纵向扩展。 优先级 -10 保留给超量预配 Pod。 有关详细信息,请参阅将群集自动缩放程序与 Pod 优先级和抢占结合使用

  • 请勿将其他节点自动缩放机制(例如虚拟机规模集自动缩放程序)与群集自动缩放程序结合使用

  • 如果 Pod 无法移动,群集自动缩放程序可能无法缩减规模,例如在以下情况下:

    • 直接创建且没有控制器对象(如 Deployment 或 ReplicaSet)作为后盾的 Pod。
    • Pod 中断预算 (PDB) 过于严格,不允许 Pod 数量降至某个阈值以下。
    • Pod 使用了节点选择器或反亲和性规则,如果调度到其他节点则无法满足这些规则。 有关详细信息,请参阅哪些类型的 Pod 可防止群集自动缩放程序移除节点?

重要

不要对自动缩放节点池中的单个节点进行更改。 同一节点组中的所有节点都应具有一致的容量、标签、污点以及其上运行的系统 Pod。

  • 集群自动扩缩器并不负责在不考虑 Pod 调度因素的情况下,对集群节点池强制执行“最大节点数”限制。 如果任何非群集自动缩放程序执行组件将节点池计数设置为超出群集自动缩放程序配置的最大值的数字,则群集自动缩放程序不会自动移除节点。 群集自动缩放的缩减行为仍限于删除未充分利用的节点。 群集自动缩放程序的最大节点计数配置的唯一用途是强制实施纵向扩展操作的上限。 它不会对缩容相关考量产生任何影响。

集群自动缩放程序配置文件

群集自动缩放程序配置文件是一组控制群集自动缩放程序行为的参数。 可以在创建群集或更新现有群集时配置群集自动缩放器配置文件。

优化集群自动扩缩容器配置文件

应根据特定的工作负载场景微调群集自动缩放程序配置文件设置,同时还要考虑性能和成本之间的权衡。 本部分提供了演示这些权衡的示例。

请务必注意,群集自动缩放程序配置文件设置是群集范围的,并应用于所有启用自动缩放的节点池。 在一个节点池中执行的任何缩放操作都可能会影响其他节点池的自动缩放行为,这可能会导致意外结果。 务必在所有相关节点池中应用一致且同步的配置文件配置,以确保获得所需的结果。

示例 1:优化性能

对于处理大量突发工作负荷且主要关注性能的群集,请增加 scan-interval 和减少 scale-down-utilization-threshold。 这些设置有助于将多个缩放操作批处理到单个调用中,从而优化缩放时间和计算读取/写入配额的利用率。 它们还有助于降低在未充分利用的节点上快速缩减操作的风险,从而提高 Pod 计划效率。 此外,增加 ok-total-unready-countmax-total-unready-percentage

对于具有 daemonset Pod 的群集,建议将 ignore-daemonsets-utilization 设置为 true,这可以有效地忽略 daemonset Pod 的节点利用率,并最大程度地减少不必要的纵向缩减操作。 请参阅适用于突发型工作负载的配置

示例 2:优化成本

如果您想使用成本优化配置,我们建议您将以下参数设置为:

  • 减少 scale-down-unneeded-time,即节点在被视为不再需要后,符合缩容条件之前所需的时间。
  • 减少 scale-down-delay-after-add,即添加节点后在考虑纵向缩减节点之前等待的时间。
  • 增加 scale-down-utilization-threshold,即删除节点的利用率阈值。
  • 增加 max-empty-bulk-delete,即可以在单个调用中删除的最大节点数。
  • skip-nodes-with-local-storage设置为 false。
  • 增加 ok-total-unready-countmax-total-unready-percentage

常见问题和缓解建议

通过CLI 或门户网站查看缩放失败和未触发扩容的事件。

未触发扩容操作

常见原因 缓解建议
PersistentVolume 节点亲和性冲突,可能会在将集群自动扩缩器与多个可用区配合使用时出现,或者在 Pod 或持久卷所在的可用区与节点所在的可用区不一致时出现。 为每个可用性区域使用一个节点池并启用 --balance-similar-node-groups。 还可以在 Pod 规范中将 volumeBindingMode 字段设置为 WaitForFirstConsumer,以防止卷在创建使用该卷的 Pod 之前绑定到节点上。
污点和容忍/节点亲和性冲突 检查分配给节点的污点,并查看在 Pod 中定义的容忍度。 如有必要,请调整污点和容忍,以确保 Pod 能够高效地调度到节点上。
限制性 Pod 拓扑分布约束 群集自动缩放程序在启动扩容作业之前运行调度模拟。 如果它确定由于限制性的拓扑分布约束而无法在新节点上调度 Pod,则不会尝试扩展规模。 若要缓解此问题,请考虑放宽拓扑分布约束。

扩容操作失败

常见原因 缓解建议
子网中的 IP 地址耗尽 在同一虚拟网络中添加另一个子网,并将另一个节点池添加到新子网中。
核心配额耗尽 批准的核心配额已耗尽。 当群集自动缩放程序经历多次失败的纵向扩展尝试时,会在特定节点组内进入指数退避状态
节点池的最大大小 增加节点池中的最大节点数或创建新的节点池。
请求/调用超出速率限制 请参阅“429 请求过多”错误

缩减操作失败

常见原因 缓解建议
Pod 阻止节点耗尽/无法逐出 Pod • 查看哪些类型的 Pod 会阻止缩容
• 对于使用本地存储的 Pod(如 hostPath 和 emptyDir),请将集群自动扩缩容器的配置标志 skip-nodes-with-local-storage 设置为 false
• 在 Pod 规范中,将 cluster-autoscaler.kubernetes.io/safe-to-evict 注释设置为 true
• 检查您的 PDB,因为它可能受到限制。
节点池的最小大小 减小节点池的最小大小。
请求/调用超出速率限制 请参阅“429 请求过多”错误
写入操作被锁定 请勿对完全托管的 AKS 资源组进行任何更改(请参阅 AKS 支持策略)。 删除或重置之前应用于资源组的任何资源锁

其他问题

常见原因 缓解建议
优先级配置映射不匹配组 务必将需要自动缩放的所有节点组添加到扩展器配置文件中。

节点池处于退避状态

版本 0.6.2 引入了处于退避状态的节点池,这会导致集群自动扩缩器在发生故障后暂缓对该节点池进行扩缩。

根据缩放操作遇到故障的时间长短,可能需要最长 30 分钟的时间才能再次尝试。 可以通过禁用然后再重新启用自动缩放来重置节点池的回退状态。