ACK Pro版集群的调度器提供负载感知调度能力,可以感知集群内节点负载情况,将Pod优先调度到负载较低的节点,实现节点负载均衡,避免出现因单个节点负载过高而导致的应用程序或节点故障。本文介绍如何使用负载感知调度。

索引

前提条件

使用限制

仅支持ACK Pro版集群。关于如何创建ACK Pro版集群,请参见创建ACK Pro版集群

负载感知调度介绍

负载感知调度是ACK调度器Kube Scheduler基于Kubernetes Scheduling Framework实现的插件。与K8s原生调度策略不同的是,原生调度器主要基于资源的分配率情况进行调度,而ACK调度器可以感知节点实际的资源负载情况。通过参考节点负载的历史统计并对新调度Pod进行预估,调度器会将Pod优先调度到负载较低的节点,实现节点负载均衡的目标,避免出现因单个节点负载过高而导致的应用程序或节点故障。

如下图所示,已分配资源量(Requested)代表已申请的资源量,已使用资源量(Usage)代表真实使用的资源量,只有真实使用的资源才会被算作真实负载。面对相同的节点情况,ACK调度器会采用更优的策略,将新创建的Pod分配到负载更低的节点B。

1

考虑到节点的利用率会随着时间、集群环境、工作负载的流量或请求等动态变化,ack-koordinator组件还提供重调度能力,防止在Pod调度完成后,集群再次出现负载极端不均衡的情况。通过将负载感知调度和热点打散重调度结合使用,可以获得集群最佳的负载均衡效果。关于热点打散重调度,请参见使用负载热点打散重调度

工作原理

负载感知调度功能由ACK调度器和ack-koordinator组件配合完成。其中,ack-koordinator负责节点资源利用率的采集和上报,ACK调度器会根据利用率数据对节点进行打分排序,优先选取负载更低的节点参与调度。关于ack-koordinator组件架构的详细介绍,请参见ack-koordinator组件架构

策略说明

策略名称说明
节点排序负载感知调度插件考虑CPU和内存两个资源维度。调度器在为节点打分时采用了加权的计算方式,优先选取分数更高的节点参与调度。CPU和内存权重支持自定义配置,详细信息,请参见Kube Scheduler参数配置

计算公式:((1 - CPU资源利用率) * CPU权重配置 + (1 - 内存资源利用率) * 内存权重配置)/(CPU权重 + 内存权重),其中CPU和内存的资源利用率单位为百分比。

资源利用率统计算法资源利用率的统计算法支持多种类型的配置,包括平均值和分位值。默认为近5分钟的平均值,详细信息,请参见Kube Scheduler参数配置

步骤一:开启负载感知调度能力

重要 请务必完成ack-koordinator组件的安装,且版本为1.1.1-ack.1及以上,否则负载感知调度能力无法生效。
  1. 登录容器服务管理控制台,在左侧导航栏选择集群
  2. 集群列表页面,单击目标集群名称,然后在左侧导航栏,选择运维管理 > 组件管理
  3. 组件管理页面,查找Kube Scheduler,然后在Kube Scheduler卡片中单击配置
  4. Kube Scheduler 参数配置对话框,选中Pod调度时启用负载感知调度能力,参考下表按需进行相关配置,然后单击确定
    下表介绍主要配置项,其余的请参见使用调度器自定义参数
    配置项类型说明取值示例值
    loadAwareResourceWeight由资源名resourceName和权重resourceWeight组成的列表。资源类型对应的打分权重。
    • resourceName:支持cpumemory两种类型。
    • resourceWeight:[1,100]。

    默认值为cpu=1, memory=1。

    • resourceName:cpu
    • resourceWeight:1
    loadAwareAggregatedUsageAggragationType枚举类型。负载统计值的聚合类型。各类型具体含义为:
    • avg:平均值。
    • p50:50%分位值,即中位数。
    • p90p95p99:分别表示90%,95%,99%分位值。
    • avg
    • p50
    • p90
    • p95
    • p99

    默认值为avg

    p90
    在左侧导航栏,单击集群信息,然后在右侧页面单击基本信息页签,等待集群状态变为运行中,表示负载感知调度能力开启成功。

步骤二:验证负载感知调度能力

下文以拥有3台4核 16 GiB节点的集群为例进行说明。

  1. 使用如下YAML内容,创建stress-demo.yaml文件。
    展开查看详细YAML文件。
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: stress-demo
      namespace: default
      labels:
        app: stress-demo
    spec:
      replicas: 1
      selector:
        matchLabels:
          app: stress-demo
      template:
        metadata:
          name: stress-demo
          labels:
            app: stress-demo
        spec:
          containers:
            - args:
                - '--vm'
                - '2'
                - '--vm-bytes'
                - '1600M'
                - '-c'
                - '2'
                - '--vm-hang'
                - '2'
              command:
                - stress
              image: polinux/stress
              imagePullPolicy: Always
              name: stress
              resources:
                limits:
                  cpu: '2'
                  memory: 4Gi
                requests:
                  cpu: '2'
                  memory: 4Gi
          restartPolicy: Always
  2. 执行如下命令,创建Pod。创建完成后,按需提升其中一个节点的负载水位。
    kubectl create -f stress-demo.yaml
    deployment.apps/stress-demo created
  3. 执行如下命令,观察Pod的状态,直到它开始运行。
    kubectl get pod -o wide
    预期输出:
    NAME                           READY   STATUS    RESTARTS   AGE   IP           NODE                    NOMINATED NODE   READINESS GATES
    stress-demo-7fdd89cc6b-g****   1/1     Running   0          82s   10.XX.XX.112   cn-beijing.10.XX.XX.112   <none>           <none>
    预期输出表明,Pod stress-demo-7fdd89cc6b-g****调度在节点cn-beijing.10.XX.XX.112上。
    等待3分钟左右,确保Pod完成初始化,节点负载水位已完成提升。
  4. 执行如下命令,检查每个节点的负载。
    kubectl top node
    预期输出:
    NAME                    CPU(cores)   CPU%   MEMORY(bytes)   MEMORY%
    cn-beijing.10.XX.XX.110   92m          2%     1158Mi          9%
    cn-beijing.10.XX.XX.111   77m          1%     1162Mi          9%
    cn-beijing.10.XX.XX.112   2105m        53%    3594Mi          28%
    预期输出表明,节点cn-beijing.10.XX.XX.111负载最低,节点cn-beijing.10.XX.XX.112的负载最高,此时集群已经出现节点负载不均的情况。
  5. 使用以下YAML内容,创建nginx-with-loadaware.yaml文件。
    展开查看详细YAML文件。
    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: nginx-with-loadaware
      namespace: default
      labels:
        app: nginx
    spec:
      replicas: 6
      selector:
        matchLabels:
          app: nginx
      template:
        metadata:
          name: nginx
          labels:
            app: nginx
        spec:
          containers:
          - name: nginx
            image: nginx
            resources:
              limits:
                cpu: 500m
              requests:
                cpu: 500m
  6. 执行如下命令,创建Pod。
    kubectl create -f nginx-with-loadaware.yaml
    deployment/nginx-with-loadawre created
  7. 执行如下命令,查看Pod调度详情。
    kubectl get pods | grep nginx
    预期输出:
    nginx-with-loadaware-5646666d56-2****   1/1     Running   0          18s   10.XX.XX.118   cn-beijing.10.XX.XX.110   <none>           <none>
    nginx-with-loadaware-5646666d56-7****   1/1     Running   0          18s   10.XX.XX.115   cn-beijing.10.XX.XX.110   <none>           <none>
    nginx-with-loadaware-5646666d56-k****   1/1     Running   0          18s   10.XX.XX.119   cn-beijing.10.XX.XX.110   <none>           <none>
    nginx-with-loadaware-5646666d56-q****   1/1     Running   0          18s   10.XX.XX.113   cn-beijing.10.XX.XX.111   <none>           <none>
    nginx-with-loadaware-5646666d56-s****   1/1     Running   0          18s   10.XX.XX.120   cn-beijing.10.XX.XX.111   <none>           <none>
    nginx-with-loadaware-5646666d56-z****   1/1     Running   0          18s   10.XX.XX.116   cn-beijing.10.XX.XX.111   <none>           <none>
    预期输出表明,集群开启负载感知调度功能后,能感知节点负载,通过运用调度策略将Pod优先调度到除cn-beijing.10.XX.XX.112以外的节点上。

相关操作

修改负载感知调度配置

  1. 登录容器服务管理控制台,在左侧导航栏选择集群
  2. 集群列表页面,单击目标集群名称,然后在左侧导航栏,选择运维管理 > 组件管理
  3. 组件管理页面,查找Kube Scheduler,然后在Kube Scheduler卡片中单击配置
  4. Kube Scheduler 参数配置对话框,修改负载感知调度的相关配置参数,单击确定
    在左侧导航栏,单击集群信息,然后在右侧页面单击基本信息页签,等待集群状态变为运行中,表示更新完成。

关闭负载感知调度插件

Kube Scheduler 参数配置对话框,取消选中Pod调度时启用负载感知调度能力,单击确定

在左侧导航栏,单击集群信息,然后在右侧页面单击基本信息页签,等待集群状态变为运行中,表示更新完成。

常见问题

调度器升级为新版本后,是否继续支持已通过旧版本协议使用的负载感知调度功能?

如需使用旧版本的负载感知调度功能,需为Pod添加Annotation alibabacloud.com/loadAwareScheduleEnabled: "true"

ACK调度器兼容旧版本协议,您可无缝升级至新版本。升级后,建议您通过步骤一:开启负载感知调度能力为调度器开启全局的负载均衡调度策略,以减少对Pod配置的改动。
重要 ACK调度器在1.22版本将持续保持对旧版本协议的兼容,在1.24版本的兼容期限截止至2023年08月30日。建议您升级集群版本,并使用新版本的负载感知调度功能配置方式。关于集群升级,请参见升级ACK集群K8s版本

各版本协议的支持情况和组件版本要求具体如下。

ACK 1.24版本
ACK调度器版本ack-koordinator(ack-slo-manager)版本要求Pod Annotation协议控制台参数配置开关
≥v1.24.6-ack-4.0≥1.1.1-ack.1支持支持
≥v1.24.6-ack-3.1且<v1.24.6-ack-4.0≥0.8.0支持不支持
ACK 1.22及以下版本
ACK调度器版本ack-koordinator(ack-slo-manager)版本要求Pod Annotation协议控制台参数配置开关
≥1.22.15-ack-4.0≥1.1.1-ack.1支持支持
≥1.22.15-ack-2.0且<1.22.15-ack-4.0≥0.8.0支持不支持
  • ≥v1.20.4-ack-4.0且≤v1.20.4-ack-8.0
  • v1.18-ack-4.0
≥0.3.0且<0.8.0支持不支持