通过ElasticQuotaTree与任务队列提升资源利用率

更新时间:2025-02-17 08:51:02

为了让不同团队和任务共享集群中的计算资源,同时确保资源的合理分配和隔离,您可以基于ack-kube-queue、ElasticQuotaTreeack-scheduler实现资源的合理、灵活分配。ack-kube-queue能够管理AI/ML和批处理工作负载的任务队列;ElasticQuotaTree支持细粒度的资源配额管理;ack-scheduler负责选择最合适的节点来运行任务。

前提条件

安装ack-kube-queue组件

通过ElasticQuotaTree提交资源配额

通过在ACK集群中使用ElasticQuotaTree,可以在限定的资源范围内高效地安排作业,确保每个团队充分利用分配资源,避免浪费和竞争。ElasticQuotaTree采用树形结构,明确每个团队或个人可使用的资源量或机器数量,在团队提交对应的作业后,系统会自动检查该任务作业所属的资源配额是否足以满足其需求。只有确保资源配额满足时, 任务作业才会被分配到相应的计算资源上并开始执行。如果某一资源配额的最低保障无法得到满足,调度系统将从实际占用超过其最低保障资源量的其他团队配额中回收资源来运行任务。

以下图为例,在某企业中,运维部门、算法部门的文本团队和视频团队、以及基础设施部门的测试团队,分别在各自的命名空间下获得了不同的CPU、内存和GPU资源配额。

image

ElasticQuotaTree提交资源配额的注意事项及示例如下。

  • 只有叶子节点可以挂载命名空间,父节点不能挂载。

  • 同一节点Min值小于等于Max值。

  • 父节点Min值必须大于等于对应子节点的Min值之和。

  • 父节点Max值必须大于等于对应任意子节点的Max值。

---
apiVersion: v1
kind: Namespace
metadata:
  name: devops 
---
apiVersion: v1
kind: Namespace
metadata:
  name: text1 
---
apiVersion: v1
kind: Namespace
metadata:
  name: text2 
---
apiVersion: v1
kind: Namespace
metadata:
  name: video 
---
apiVersion: v1
kind: Namespace
metadata:
  name: test1 
---
apiVersion: v1
kind: Namespace
metadata:
  name: test2 
---
apiVersion: scheduling.sigs.k8s.io/v1beta1
kind: ElasticQuotaTree
metadata:
  name: elasticquotatree # 当前仅支持单一ElasticQuotaTree。
  namespace: kube-system # 只有kube-system下才会生效。
spec:
  root:
    name: root 
    min:       # Min默认值为0,表示没有保障资源(Guaranteed Resource),但是您依然可以提交作业。
      cpu: 100
      memory: 50Gi
      nvidia.com/gpu: 16
    max:       # Max默认值为NA,表示最大可用的资源数不受限制。
      cpu: 100
      memory: 50Gi
      nvidia.com/gpu: 16
    children:
    - name: devops 
      min:
        cpu: 20
        memory: 10Gi
        nvidia.com/gpu: 4 
      max:
        cpu: 40
        memory: 20Gi
        nvidia.com/gpu: 8 
      namespaces: # 配置对应的Namespace。
      - devops 
    - name: algorithm  
      min:
        cpu: 50
        memory: 25Gi
        nvidia.com/gpu: 10 
      max:
        cpu: 80
        memory: 50Gi
        nvidia.com/gpu: 14 
      children:
      - name: text 
        min:
          cpu: 40
          memory: 15Gi
          nvidia.com/gpu: 8 
        max:
          cpu: 40
          memory: 30Gi
          nvidia.com/gpu: 10 
        namespaces: # 配置对应的Namespace。
        - text1 
        - text2 
      - name: video 
        min:
          cpu: 12
          memory: 12Gi
          nvidia.com/gpu: 2 
        max:
          cpu: 14
          memory: 14Gi
          nvidia.com/gpu: 4 
        namespaces: # 配置对应的Namespace。
        - video 
    - name: infrastructure  
      min:
        cpu: 30
        memory: 15Gi
        nvidia.com/gpu: 2 
      max:
        cpu: 50
        memory: 30Gi
        nvidia.com/gpu: 4 
      children:
      - name: test
        min:
          cpu: 30
          memory: 15Gi
          nvidia.com/gpu: 2 
        max:
          cpu: 50
          memory: 30Gi
          nvidia.com/gpu: 4 
        namespaces: # 配置对应的Namespace。
        - test1 
        - test2

ack-kube-queue管理任务队列

任务队列Queue能够将来自不同部门和团队的作业分配到相应的队列。在ElasticQuotaTree提交后,ack-kube-queue会在集群中自动创建相应的Queue用于任务排队。每个叶子节点的资源配额映射到集群中的一个独立Queue。当作业被提交到集群时,ack-kube-queue会自动为其创建QueueUnit对象,QueueUnit作为KubeQueue中资源分配的单位,会自动与作业关联。根据QueueUnit所属命名空间及其资源配额中的关联关系,ack-kube-queue会自动将任务分配到相应的队列中。

RayJob为例,视频团队将video关联到特定的命名空间,并通过minmax配置资源配额。ack-kube-queue会自动为此配额创建关联的Queue:root-algorithm-video,后续在video命名空间下提交RayJob对象后,会自动创建对应的QueueUnit资源对象,并进入root-algorithm-video队列进行排队。如果RayJob所请求的资源总量满足当前的可用配额管理要求,则RayJob会从root-algorithm-video中出队,并进入调度器逻辑进行处理。

image

ElasticQuotaTreeQueue自动关联逻辑

ack-kube-queue中,有一个控制器逻辑可以自动管理集群内的队列资源。这一逻辑会根据ElasticQuotaTree资源来维护,并将ElasticQuotaTree中定义的配额与命名空间的关联关系映射到相应的队列上。

image

Queue队列操作逻辑

RayJob为例,当创建一个suspend设置为trueRayJob时,首先会被ack-kube-queue检测到,并相应创建一个QueueUnit对象。该QueueUnit会在对应的队列中排队,按照排队策略的条件出队后,ack-kube-queue组件会将该RayJobsuspend字段设为false。此时,进入KubeRay Operator的调和逻辑,开始创建Pod,最终Pod将进入调度器的调度流程。

image
  • 本页导读 (1)
  • 前提条件
  • 通过ElasticQuotaTree提交资源配额
  • ack-kube-queue管理任务队列
  • ElasticQuotaTree与Queue自动关联逻辑
  • Queue队列操作逻辑