Job 怎么控制并行度?失败了会重试几次、多久重试一次?Pod 会不会被留下来?这篇用同一个 busybox 容器,把 completions、parallelism、backoffLimit、两种 restartPolicy、deadline、suspend 和 TTL 都实测了一遍。
(active, succeeded) 的变化:(2, 0)@0.1s → (2, 2)@6.0s → (2, 4)@12.0s → (0, 6)@18.0s
最多同时 2 个 Pod 在跑;总共 6 个 Pod;conditions=[('SuccessCriteriaMet', 'True'), ('Complete', 'True')];startTime→completionTime 用了 18 秒
completionMode: Indexed(4 个):idx-0-4qgz2→index 注解 0、日志「我是第 0 个」; idx-1-rvd82→index 注解 1、日志「我是第 1 个」; idx-2-s9xvr→index 注解 2、日志「我是第 2 个」 …completions: 6、parallelism: 2,每个 Pod 睡 3 秒:active 始终是 2,succeeded 以 2 为步长涨到 6,3 批共 18 秒(每批还包含调度与启动的开销)。completionMode: Indexed 给每个 Pod 一个序号(注解 batch.kubernetes.io/job-completion-index,环境变量 JOB_COMPLETION_INDEX),分片处理数据时很方便。
fail-never(backoffLimit 2,restartPolicy: Never):每次失败都新建一个 Pod:共 3 个 Pod,创建时刻(相对第一个)[0, 10, 30] 秒(间隔 10 秒、20 秒的指数退避);status.failed=3;33 秒时 Failed:reason=BackoffLimitExceeded message=Job has reached the specified backoff limit fail-onfail(backoffLimit 2,restartPolicy: OnFailure):始终只有 1 个 Pod,容器在原地重启,轮询到的最大 restartCount=2;15 秒时 Failed:reason=BackoffLimitExceeded;失败后 Pod 数 0(Job 失败时把 Pod 删除了);status.failed=1
backoffLimit: 2 的 Job 总是 exit 1。restartPolicy: Never:每次失败都新建一个 Pod,创建时刻 0、10、30 秒(退避 10 秒、20 秒),共 3 个 Pod 全部保留,方便逐个看日志,33 秒后 Job Failed,reason: BackoffLimitExceeded。restartPolicy: OnFailure:始终是同一个 Pod,容器在原地重启,重启次数也计入 backoffLimit(restartCount 到 2),15 秒后 Job 同样失败,并且 Job 失败时把这个 Pod 删掉了——想留日志就用 Never。
activeDeadlineSeconds=8、容器 sleep 60:8.8 秒后 Job 条件 Failed reason=DeadlineExceeded message=Job was active longer than specified deadline;active=0;Pod:(已被删除)
activeDeadlineSeconds: 8、容器 sleep 60:8.8 秒后 Job 失败,reason: DeadlineExceeded,还在运行的 Pod 被终止并删除。它限制的是整个 Job 的存活时间,无论重试了几次。
suspend: true 创建 4 秒后:Pod 数 0;conditions=[('Suspended', 'True', 'JobSuspended')]
取消暂停之后 4.8 秒 Job Complete;Pod 数 1
ttlSecondsAfterFinished=8:Complete 之后 7.8 秒 Job 与它的 Pod 被自动删除:Job 已删除;剩余 Pod 0 个suspend: true 的 Job 创建后不产生任何 Pod,条件 Suspended;改成 false 之后 4.8 秒就跑完了。ttlSecondsAfterFinished: 8 让 Job 完成 7.8 秒后连同 Pod 被自动删除;不设的话 Job 和 Pod 会一直留着,日积月累就是对象泄漏。