
# Volcano Job
随着人工智能、大数据分析和高性能计算（HPC）等场景的快速发展，传统Kubernetes Job在复杂任务调度、资源保障、任务依赖等方面逐渐显现出局限性。为解决这些问题，CCE Standard/Turbo 集群基于**Volcano** 提供了 **Volcano Job（简称 vcjob）** 功能。Volcano是一个面向批处理与高性能计算场景的Kubernetes原生调度系统，提供了比原生Job更强大的作业管理能力。
通过 Volcano Job，用户可以：
- 定义包含多个任务类型的复杂作业（如 MPI、Spark、TensorFlow 等）。
- 设置最小成功 Pod 数（minAvailable），保障作业执行的可靠性。
- 指定专用调度器（如 volcano）进行资源调度。
- 支持任务间依赖关系、索引型任务（Indexed Job）等高级特性。
#### 基本概念
| 概念                     | 定义                                                    | 作用                                                     |
|:---|:---|:---|
| **Volcano Job（vcjob）** | Volcano 自定义的 Job 资源类型，扩展了 Kubernetes 原生 Job 的能力       | 支持多任务模板、最小运行 Pod 数、任务依赖、索引任务等，适用于 AI 训练、基因测序等批处理场景     |
| **Task**               | Volcano Job 中的一个任务单元，可定义多个不同类型的 Task（如 master、worker） | 每个 Task 可拥有独立的容器镜像、资源请求、副本数等，实现异构任务编排                  |
| **MinAvailable**       | 作业成功运行所需的最小 Pod 数量                                    | 若实际成功运行的 Pod 数小于该值，则整个作业被视为失败，避免部分成功导致结果不可靠            |
| **SchedulerName**      | 指定用于调度该 Job 的调度器名称（通常为 volcano）                       | 确保作业由 Volcano 调度器处理，启用高级调度策略（如 gang scheduling）        |
| **Queue**              | Volcano 提供的资源队列机制，用于对作业进行分组和优先级管理                     | 支持多租户资源隔离、配额控制和优先级调度                                   |
| **Policy**             | 定义在特定事件（如 Pod 失败、任务完成）发生时应采取的动作                       | 支持自动重启、完成作业、终止作业等行为，提升作业鲁棒性和自动化程度                      |
| **Plugin**             | Volcano 提供的作业增强插件机制，用于自动注入框架所需的环境变量或启动参数              | 如 pytorch 插件可自动配置 MASTER_ADDR、RANK、WORLD_SIZE 等分布式训练参数 |
   
#### 前提条件
- 已创建 CCE Standard/Turbo 集群，集群版本建议为 v1.29 及以上。
- **已安装1.19.11及以上版本的Volcano插件**：在 CCE 控制台"插件中心"中搜索并安装 "Volcano 调度器" 插件。
- 集群节点具备足够的 CPU、内存等资源以运行批处理任务。
- （可选）若需使用 Queue 功能，需提前通过 kubectl 创建 Volcano Queue 资源。
![](https://support.huaweicloud.com/usermanual-cce/public_sys-resources/caution_3.0-zh-cn.png)
在使用 Volcano 作为调度器时，建议将集群中所有相关工作负载统一使用 Volcano 调度，以避免调度冲突。
#### 约束与限制
- Volcano Job 依赖 Volcano 调度器插件，未安装插件时无法生效。
- 当前 CCE 控制台暂不支持图形化创建 vcjob，需通过 kubectl 或 YAML 文件部署。
- 若使用 minAvailable，需确保集群资源充足，否则可能导致作业长期处于 Pending 状态。
- Volcano Job 不支持与 Kubernetes CronJob 直接集成，需通过外部控制器实现定时触发。
 
#### 使用示例：使用 Volcano Job 运行 PyTorch 分布式训练
以下 YAML 示例展示如何使用 Volcano Job 启动一个包含 **1 个 master + 2 个 worker** 的 PyTorch 分布式训练任务，并利用 **Policy** 和 **PyTorch Plugin** 实现高可靠性和自动配置。
```
apiVersion: batch.volcano.sh/v1alpha1
kind: Job
metadata:
  name: resnet-dist-train
spec:
  # 至少需要 3 个 Pod（1 master + 2 worker）同时成功运行，作业才算成功
  minAvailable: 3
  # 指定使用 Volcano 调度器，启用 Gang Scheduling 等高级调度能力
  schedulerName: volcano
  # 定义作业级策略：当有 Pod 被驱逐（PodEvicted）或失败（PodFailed）时，
  # 执行 RestartJob 动作 —— 重建整个 Job 的所有 Pod。
  # 这对分布式训练至关重要，可避免部分节点失败导致训练不同步。
  policies:
    - events: [PodEvicted, PodFailed]
      action: RestartJob
  # 启用 PyTorch 插件，自动注入分布式训练所需的环境变量和启动参数。
  # 插件会根据 tasks 中的 master/worker 名称和副本数，
  # 自动设置 MASTER_ADDR、RANK、WORLD_SIZE、MASTER_PORT 等。
  plugins:
    pytorch: ["--master=master", "--worker=worker", "--port=23456"]
    status-mounter: ["-statusJson=true","-mountPoint=/status","-values=retryCount,pending,running"]
  tasks:
    # Master 任务：负责协调训练过程
    - replicas: 1
      name: master
      # Task 级策略：当 master 任务完成时，自动标记整个 Job 为完成状态
      policies:
        - event: TaskCompleted
          action: CompleteJob
      template:
        spec:
          containers:
            - image: gcr.io/kubeflow-ci/pytorch-dist-sendrecv-test:1.0
              imagePullPolicy: IfNotPresent
              name: master
          restartPolicy: OnFailure
    # Worker 任务：执行实际的模型训练
    - replicas: 2
      name: worker
      template:
        spec:
          containers:
            - image: gcr.io/kubeflow-ci/pytorch-dist-sendrecv-test:1.0
              imagePullPolicy: IfNotPresent
              name: worker
              workingDir: /home
          restartPolicy: OnFailure
```
#### 关键特性解析
**Policy（策略）机制**
- **作业级策略**（spec.policies）：适用于整个 Job。例如，当任意 Pod 失败时，RestartJob 会销毁所有 Pod 并重新创建，确保分布式训练从一致状态开始。
- **任务级策略**（tasks\[\].policies）：适用于单个 Task。例如，TaskCompleted 事件触发 CompleteJob，可用于 master 完成后自动结束整个作业。
**PyTorch Plugin（插件）**
- Volcano 内置 pytorch 插件，可自动为容器注入以下环境变量：
  - MASTER_ADDR：master Pod 的 IP 地址
  
  - MASTER_PORT：由 --port 指定（本例为 23456）
  
  - WORLD_SIZE：总进程数（= master 1 + worker 2 = 3）
  
  - RANK：每个 Pod 的唯一序号（master 通常为 0，worker 依次为 1、2...）
   
- 用户无需手动编写服务发现或 IP 配置逻辑，极大简化分布式训练部署。
  ![](https://support.huaweicloud.com/usermanual-cce/public_sys-resources/note_3.0-zh-cn.png)
  该插件要求容器内使用 torch.distributed 启动方式（如 torch.distributed.run 或 torch.distributed.launch），并读取上述环境变量。
  
**status-mounter Plugin（插件）**
Volcano 内置 status-mounter 插件，可自动将vcjob的状态通过环境变量或者通过文件挂载注入容器 插件支持如下配置：
- 挂载路径 mountPoint: 用于指定状态信息写入的文件路径。若未设置，则不会进行文件挂载 示例配置：-mountPoint="/status"
- 环境变量注入开关 addEnv: 控制是否将状态信息注入为容器的环境变量。默认为启用状态 示例配置：-addEnv=true
- 状态值列表 values: 定义需要注入的 vcjob 状态字段。默认仅包含 retryCount 示例配置：-values=retryCount,pending,running 表示将 retryCount、pending 和 running 三个状态值注入容器。
- 状态 JSON 序列化开关 statusJson: 决定是否将整个 vcjob 的状态对象序列化为 JSON 格式并挂载。默认为关闭 示例配置：-statusJson=true 启用后，会生成一个名为 jsonStatus 的字段，内容为完整的 JSON 格式状态数据
- 环境变量前缀 prefix: 设置注入环境变量时的前缀名称。默认为 Job_ 示例配置：-prefix=Job_ 最终环境变量名称如 Job_retryCount、Job_pending 等
- 容器过滤器 containers: 用于指定状态注入的目标容器。默认为 \*，表示对所有容器生效 示例配置：-containers=\*
 
#### 部署与验证
1. 应用YAML 
   ```
   kubectl apply -f resnet-dist-train.yaml
   ```
   
   
2. 查看状态 
   ```
   # 查看 Job 状态
   kubectl get vcjob resnet-dist-train
   # 查看 Pod
   kubectl get pods -l volcano.sh/job-name=resnet-dist-train
   # 查看日志（例如查看 worker-0）
   kubectl logs resnet-dist-train-worker-0
   ```
   当 Job 状态为 Completed 时，表示训练成功完成。
   在训练过程中，可以通过读取插件注入的环境变量或挂载文件，来实时监控分布式任务的运行状态。这种方式能够帮助判断当前任务的调度和执行情况，从而进行相应的调整或决策。 例如，status-mounter 插件将任务状态写入指定路径下的文件，用户可以通过执行命令查看这些状态值：
   ```
   kubectl exec resnet-dist-train-worker-0 -- cat /status/pending
   1
   kubectl exec resnet-dist-train-worker-0 -- cat /status/running
   2
   ```
   从上述输出可以看出，当前有 1 个 Pod 处于待启动状态，2 个 Pod 正在运行中。结合这些信息，可以判断任务尚未完全启动，仍有一个工作节点等待调度。 这种方式不仅便于调试，也适用于在训练脚本中动态读取状态，实现更智能的任务控制和资源管理。
   
   
 
#### 组件说明
Volcano Job 依赖以下核心组件（均部署在 kube-system 命名空间）：
| 组件名称                | 说明                                | 资源类型       |
|:---|:---|:---|
| volcano-admission   | 准入控制器，校验 vcjob 配置合法性              | Deployment |
| volcano-controllers | 控制器，管理 Job、Queue、PodGroup 等资源生命周期 | Deployment |
| volcano-scheduler   | 核心调度器，实现 Gang Scheduling、优先级调度等策略 | Deployment |
   
#### 常见问题
- **Volcano Job 和 Kubernetes 原生 Job 有何区别？**
  Volcano Job 支持多 Task、minAvailable、Queue、Gang Scheduling 等高级特性，更适合 AI/HPC 批处理场景；而原生 Job 仅支持单一 Pod 模板和简单重试机制。
  
- **如何查看 Volcano Job 的调度日志？**
  可通过以下命令查看调度器日志：
  ```
  kubectl logs -n kube-system -l app=volcano-scheduler
  ```
  
 
