3. Volcano核心概念与API对象
Volcano 的调度能力并不是直接作用在单个 Pod 上,而是通过一组自定义资源(CRD)把“批量作业”的语义显式建模出来。理解 Queue、PodGroup、Job、JobFlow 这四类对象,以及它们之间的引用关系和生命周期,是后续做队列配额、gang 调度、作业编排和故障排查的基础。可以把它们理解为四个层次:Queue 管资源池与配额,PodGroup 管一组 Pod 的调度单元与 gang 约束,Job 管一类批处理作业的完整生命周期,JobFlow 管多个 Job 之间的依赖与编排。
Queue:资源池、配额与调度优先级
Queue 是 Volcano 中的资源队列,属于集群级资源(cluster-scoped)。它把一个物理集群划分成多个逻辑资源池,每个队列可以设置权重、资源上限和应得资源。调度器在为 PodGroup 分配资源时,会先看它属于哪个 Queue,再在该 Queue 的配额范围内做分配。Queue 的核心字段包括:
spec.weight:队列权重,用于在多个队列竞争空闲资源时按比例分配,权重越大分到的资源越多。spec.capability:队列可使用的资源上限,例如cpu: 20、memory: 40Gi,超过上限的 PodGroup 不会被调度。spec.guarantee:队列的保障资源,即无论其他队列如何竞争,该队列至少能拿到的资源量。spec.deserved:应得资源,通常由权重和总资源计算得出,用于描述队列“理论上应分到多少”。status.state:队列状态,常见为Open、Closed、Unknown;Closed时不再接受新的 PodGroup 入队。
Queue 的生命周期相对简单:创建后处于 Open 状态,可被 PodGroup 引用;当管理员将其置为 Closed 时,已有作业继续运行,但新作业无法入队;删除 Queue 前需要确保没有 PodGroup 仍在引用它,否则相关作业会因找不到队列而无法调度。
PodGroup:调度的最小单元与 gang 约束
PodGroup 是 Volcano 调度的核心对象,它把一组需要“同生共死”的 Pod 聚合为一个调度单元。PodGroup 通常由 Job 控制器自动创建,也可以手动创建。它的关键字段包括:
spec.minMember:最小成员数,即 gang 调度要求同时满足的最少 Pod 数量。只有可调度的 Pod 数达到 minMember,整组才会被调度,否则全部等待。spec.minTaskMember:按任务类型细分的最小成员数,用于多角色作业(如 master/worker)分别约束。spec.queue:指定该 PodGroup 所属的 Queue 名称,决定它使用哪个资源池和配额。spec.priorityClassName:优先级类,影响抢占和调度顺序。status.phase:PodGroup 阶段,常见为Pending、Running、Completed、Failed。status.running/status.succeeded/status.failed:各状态下的 Pod 计数。
PodGroup 的生命周期与 gang 调度强相关:创建后进入 Pending,调度器持续尝试凑齐 minMember;一旦满足,整组进入 Running;当所有 Pod 成功结束,PodGroup 变为 Completed;若有 Pod 失败且无法恢复,则变为 Failed。理解 minMember 与 status.running 的差值,是判断“作业为什么一直不启动”的关键。
Job:面向批处理作业的控制器对象
Volcano 的 Job 是一种批处理作业抽象,它负责创建和管理一组 Pod,并自动生成对应的 PodGroup。Job 的字段设计围绕“作业完成”展开:
spec.schedulerName:必须指定为volcano,否则 Pod 不会被 Volcano 调度。spec.minAvailable:作业可运行所需的最小可用副本数,直接映射到 PodGroup 的 minMember。spec.parallelism:允许同时运行的 Pod 数量上限,用于控制并发度。spec.completions:作业成功完成所需的 Pod 总数。spec.tasks:任务模板列表,每个任务可指定副本数、模板、策略等,支持多角色作业。spec.policies:生命周期策略,例如Event: PodFailed, Action: AbortJob,用于定义失败时的处理动作。status.state:作业状态,常见为Pending、Running、Completed、Failed、Aborted。
Job 的生命周期可以概括为:提交后创建 PodGroup 并进入 Pending;调度器满足 minAvailable 后转为 Running;当成功完成的 Pod 数达到 completions 时转为 Completed;若触发失败策略或超过重试上限,则转为 Failed 或 Aborted。Job 控制器会持续同步 Pod 状态到 Job 的 status 中,因此排查时应同时查看 Job 与 PodGroup 的状态。
JobFlow:多 Job 依赖编排
JobFlow 用于描述多个 Job 之间的依赖关系,适合流水线式批处理场景。它通过 spec.flows 定义一组 Job 模板及其依赖,通过 spec.jobRetainPolicy 控制 Job 完成后是否保留。JobFlow 会按依赖顺序依次创建和运行 Job,前序 Job 成功后才触发后续 Job。其状态字段 status.state 反映整体流程进展,常见为 Running、Completed、Failed。JobFlow 的价值在于把“作业之间的先后依赖”从人工脚本提升为平台级编排对象。
四类对象的协作关系与排查要点
从引用关系看,Job 通过 spec.minAvailable 和 spec.tasks 生成 PodGroup,PodGroup 通过 spec.queue 绑定 Queue,JobFlow 则通过 spec.flows 编排多个 Job。调度器只认 PodGroup 和 Queue,因此当作业不调度时,排查顺序建议是:先看 Job 的 status.state 是否 Pending,再看 PodGroup 的 status.running 是否达到 minMember,最后看 Queue 的 capability 是否已被占满或 state 是否为 Closed。下面给出一个可直接参考的 Job 示例片段:
apiVersion: batch.volcano.sh/v1alpha1
kind: Job
metadata:
name: demo-job
spec:
schedulerName: volcano
minAvailable: 2
queue: research
tasks:
- replicas: 2
name: worker
template:
spec:
containers:
- name: c
image: busybox
command: ["sh", "-c", "echo hello && sleep 30"]
policies:
- event: PodFailed
action: AbortJob
该示例中,minAvailable: 2 表示至少 2 个 Pod 同时可调度才会启动,queue: research 表示使用 research 队列的配额,policies 表示任一 Pod 失败即中止整个作业。提交后可用 kubectl get podgroup 观察 PodGroup 的 phase 与 running 计数,用 kubectl get queue research -o yaml 查看队列的 capability 与 deserved 是否满足需求。若 PodGroup 长期 Pending 且 running 为 0,通常说明队列配额不足或 minMember 设置过大;若 running 达到 minMember 但 Job 仍不 Running,则应检查 Pod 模板本身是否可调度。