欢迎光临
我们一直在努力

Kubernetes 调度 AI 任务:如何通过 Kube-batch 解决 Pod 间的 Gang Scheduling

在分布式 AI 训练任务中(例如 PyTorch Distributed 或 Horovod),一个任务通常包含多个相互依赖的 Pods(例如一个 Master 和 N 个 Worker)。这些 Pods 必须同时启动才能开始工作。如果 Kubernetes 默认调度器只调度了 N-1 个 Pod,而第 N 个 Pod 因为资源不足无法启动,那么整个任务就会陷入等待,造成资源浪费甚至死锁。这种需求被称为 Gang Scheduling(协同调度或组调度)。

Kube-batch 是 Kubernetes 社区为了解决此类批处理和 AI 任务调度问题而诞生的项目,目前已演进为 CNCF 的顶级项目 Volcano,它作为 Kubernetes 的自定义调度器,完美地实现了 Gang Scheduling。

1. Gang Scheduling 原理

Volcano 通过引入 PodGroup 或自定义 Job CRD 来定义任务组。它确保任务组中的 Pods 满足一个最低可用数量 (minAvailable) 的要求后,才会尝试调度它们。如果集群资源无法同时满足 minAvailable 的要求,Volcano 会拒绝调度这个组中的任何 Pod,直到资源满足为止。

2. 环境准备与 Volcano 安装

要使用 Gang Scheduling,我们首先需要安装 Volcano 调度器。

步骤 1: 确保 Kubernetes 集群可用

步骤 2: 使用 Helm 安装 Volcano

Volcano 推荐使用 Helm 进行安装。这会在集群中部署 Volcano 控制器和调度器组件,并注册必要的 CRDs。

history_path=$(helm home)
if [ ! -d "$history_path" ]; then
    helm init # 首次使用需要初始化
fi

# 添加 Volcano 仓库
helm repo add volcano https://volcano.sh/charts/
helm repo update

# 安装 Volcano 到 volcano-system 命名空间
helm install volcano/volcano --name volcano --namespace volcano-system

# 验证安装
kubectl get pods -n volcano-system
# 确保 volcano-controller 和 volcano-scheduler 处于 Running 状态

3. 实现 Gang Scheduling 示例

我们将创建一个简单的分布式任务,要求至少 2 个 Pods (一个 Master, 一个 Worker) 必须同时被调度。

我们使用 Volcano 的 Job CRD 来定义任务,并设置 minAvailable 字段。

步骤 1: 创建 Volcano Job YAML (gang-scheduling-job.yaml)

apiVersion: batch.volcano.sh/v1alpha1
kind: Job
metadata:
  name: ai-gang-job
spec:
  # 指定使用 volcano 调度器
  schedulerName: volcano
  # 设定最小可用 Pod 数量。只有当集群能同时满足 2 个 Pod 时,任务才会被调度。
  minAvailable: 2
  # 定义任务组
  tasks:
    # 任务 1: Master 节点
    - name: master
      replicas: 1
      template:
        spec:
          containers:
            - name: master-container
              image: busybox
              command: ["sh", "-c", "echo 'Master Pod started' && sleep 3600"]
          # 要求更高的资源,模拟 AI 任务
          resources:
            requests:
              cpu: "100m"
    # 任务 2: Worker 节点
    - name: worker
      replicas: 1
      template:
        spec:
          containers:
            - name: worker-container
              image: busybox
              command: ["sh", "-c", "echo 'Worker Pod started' && sleep 3600"]
          resources:
            requests:
              cpu: "100m"

步骤 2: 提交任务并验证调度

# 提交 Volcano Job
kubectl apply -f gang-scheduling-job.yaml

# 检查 Job 状态
kubectl get vcjob ai-gang-job -o yaml | grep 'state'

# 检查 Pods 状态。如果调度成功,两个 Pods 会同时进入 Pending -> Running 状态。
kubectl get pods -l volcano.sh/job-name=ai-gang-job

验证结果: 如果集群资源充足,Volcano 会一次性调度 masterworker 这两个 Pod。如果在提交时,集群资源只能满足其中一个 Pod 的要求,Volcano 会暂时 HOLD 住这两个 Pod 的调度请求,直到资源完全满足 minAvailable: 2 的约束,从而避免了部分启动导致的死锁和资源浪费。

通过使用 Volcano (Kube-batch 的继任者),我们为 Kubernetes 上的高性能计算和分布式 AI 训练提供了可靠的 Gang Scheduling 机制,极大地提升了任务调度的效率和稳定性。

【本站文章皆为原创,未经允许不得转载】:汤不热吧 » Kubernetes 调度 AI 任务:如何通过 Kube-batch 解决 Pod 间的 Gang Scheduling
分享到: 更多 (0)

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址