Kubernetes 使用CronJob運行自動化任務(wù)

2022-06-15 11:57 更新

使用 CronJob 運行自動化任務(wù)

在Kubernetes v1.21 版本中,CronJob 被提升為通用版本。如果你使用的是舊版本的 Kubernetes,請參考你正在使用的 Kubernetes 版本的文檔,這樣你就能看到準確的信息。舊的 Kubernetes 版本不支持?batch/v1? CronJob API。

你可以利用 CronJobs 執(zhí)行基于時間調(diào)度的任務(wù)。這些自動化任務(wù)和 Linux 或者 Unix 系統(tǒng)的 Cron 任務(wù)類似。

CronJobs 在創(chuàng)建周期性以及重復(fù)性的任務(wù)時很有幫助,例如執(zhí)行備份操作或者發(fā)送郵件。CronJobs 也可以在特定時間調(diào)度單個任務(wù),例如你想調(diào)度低活躍周期的任務(wù)。

CronJobs 有一些限制和特點。 例如,在特定狀況下,同一個 CronJob 可以創(chuàng)建多個任務(wù)。 因此,任務(wù)應(yīng)該是冪等的。

在開始之前

你必須擁有一個 Kubernetes 的集群,同時你的 Kubernetes 集群必須帶有 kubectl 命令行工具。 建議在至少有兩個節(jié)點的集群上運行本教程,且這些節(jié)點不作為控制平面主機。 如果你還沒有集群,你可以通過 Minikube 構(gòu)建一個你自己的集群,或者你可以使用下面任意一個 Kubernetes 工具構(gòu)建:

您的 Kubernetes 服務(wù)器版本必須不低于版本 v1.21. 要獲知版本信息,請輸入 ?kubectl version?。

創(chuàng)建 CronJob

CronJob 需要一個配置文件。 本例中 CronJob 的?.spec? 配置文件每分鐘打印出當(dāng)前時間和一個問好信息:

apiVersion: batch/v1
kind: CronJob
metadata:
  name: hello
spec:
  schedule: "* * * * *"
  jobTemplate:
    spec:
      template:
        spec:
          containers:
          - name: hello
            image: busybox:1.28
            imagePullPolicy: IfNotPresent
            command:
            - /bin/sh
            - -c
            - date; echo Hello from the Kubernetes cluster
          restartPolicy: OnFailure

想要運行示例的 CronJob,可以下載示例文件并執(zhí)行命令:

kubectl create -f https://k8s.io/examples/application/job/cronjob.yaml
cronjob.batch/hello created

創(chuàng)建好 CronJob 后,使用下面的命令來獲取其狀態(tài):

kubectl get cronjob hello

輸出類似于:

NAME    SCHEDULE      SUSPEND   ACTIVE   LAST SCHEDULE   AGE
hello   */1 * * * *   False     0        50s             75s

就像你從命令返回結(jié)果看到的那樣,CronJob 還沒有調(diào)度或執(zhí)行任何任務(wù)。大約需要一分鐘任務(wù)才能創(chuàng)建好。

kubectl get jobs --watch
NAME               COMPLETIONS   DURATION   AGE
hello-4111706356   0/1                      0s
hello-4111706356   0/1           0s         0s
hello-4111706356   1/1           5s         5s

現(xiàn)在你已經(jīng)看到了一個運行中的任務(wù)被 “hello” CronJob 調(diào)度。 你可以停止監(jiān)視這個任務(wù),然后再次查看 CronJob 就能看到它調(diào)度任務(wù):

kubectl get cronjob hello

輸出類似于:

NAME    SCHEDULE      SUSPEND   ACTIVE   LAST SCHEDULE   AGE
hello   */1 * * * *   False     0        50s             75s

你應(yīng)該能看到 ?hello ?CronJob 在 ?LAST SCHEDULE? 聲明的時間點成功的調(diào)度了一次任務(wù)。 有 0 個活躍的任務(wù)意味著任務(wù)執(zhí)行完畢或者執(zhí)行失敗。

現(xiàn)在,找到最后一次調(diào)度任務(wù)創(chuàng)建的 Pod 并查看一個 Pod 的標準輸出。

說明: Job 名稱和 Pod 名稱不同。

# 在你的系統(tǒng)上將 "hello-4111706356" 替換為 Job 名稱
pods=$(kubectl get pods --selector=job-name=hello-4111706356 --output=jsonpath={.items..metadata.name})

查看 Pod 日志:

kubectl logs $pods

輸出與此類似:

Fri Feb 22 11:02:09 UTC 2019
Hello from the Kubernetes cluster

刪除 CronJob

當(dāng)你不再需要 CronJob 時,可以用 ?kubectl delete cronjob <cronjob name>? 刪掉它:

kubectl delete cronjob hello

刪除 CronJob 會清除它創(chuàng)建的所有任務(wù)和 Pod,并阻止它創(chuàng)建額外的任務(wù)。

編寫 CronJob 聲明信息

像 Kubernetes 的其他配置一樣,CronJob 需要 ?apiVersion?、?kind?、和 ?metadata ?域。

CronJob 配置也需要包括 .spec。

說明: 對 CronJob 的所有改動,特別是它的 ?.spec?,只會影響將來的運行實例。

時間安排 

?.spec.schedule? 是 ?.spec? 需要的域。它使用了 Cron 格式串,例如 ?0 * * * *? or ?@hourly? ,作為它的任務(wù)被創(chuàng)建和執(zhí)行的調(diào)度時間。

該格式也包含了擴展的 "Vixie cron" 步長值。 FreeBSD 手冊中解釋如下:

步長可被用于范圍組合。范圍后面帶有 ?/<數(shù)字>? 可以聲明范圍內(nèi)的步幅數(shù)值。 例如,?0-23/2? 可被用在小時域來聲明命令在其他數(shù)值的小時數(shù)執(zhí)行 ( V7 標準中對應(yīng)的方法是?0,2,4,6,8,10,12,14,16,18,20,22?)。 步長也可以放在通配符后面,因此如果你想表達 "每兩小時",就用 ?*/2? 。

說明: 調(diào)度中的問號 (???) 和星號 ?*? 含義相同,表示給定域的任何可用值。

任務(wù)模版

?.spec.jobTemplate?是任務(wù)的模版,它是必須的。它和 Job的語法完全一樣, 除了它是嵌套的沒有 ?apiVersion ?和 ?kind?。

開始的最后期限 

?.spec.startingDeadlineSeconds? 域是可選的。 它表示任務(wù)如果由于某種原因錯過了調(diào)度時間,開始該任務(wù)的截止時間的秒數(shù)。過了截止時間,CronJob 就不會開始任務(wù)。 不滿足這種最后期限的任務(wù)會被統(tǒng)計為失敗任務(wù)。如果該域沒有聲明,那任務(wù)就沒有最后期限。

如果?.spec.startingDeadlineSeconds?字段被設(shè)置(非空),CronJob 控制器會計算從預(yù)期創(chuàng)建 Job 到當(dāng)前時間的時間差。 如果時間差大于該限制,則跳過此次執(zhí)行。

例如,如果將其設(shè)置為 ?200?,則 Job 控制器允許在實際調(diào)度之后最多 200 秒內(nèi)創(chuàng)建 Job。

并發(fā)性規(guī)則 

?.spec.concurrencyPolicy? 也是可選的。它聲明了 CronJob 創(chuàng)建的任務(wù)執(zhí)行時發(fā)生重疊如何處理。 spec 僅能聲明下列規(guī)則中的一種:

  • ?Allow ?(默認):CronJob 允許并發(fā)任務(wù)執(zhí)行。
  • ?Forbid?: CronJob 不允許并發(fā)任務(wù)執(zhí)行;如果新任務(wù)的執(zhí)行時間到了而老任務(wù)沒有執(zhí)行完,CronJob 會忽略新任務(wù)的執(zhí)行。
  • ?Replace?:如果新任務(wù)的執(zhí)行時間到了而老任務(wù)沒有執(zhí)行完,CronJob 會用新任務(wù)替換當(dāng)前正在運行的任務(wù)。

請注意,并發(fā)性規(guī)則僅適用于相同 CronJob 創(chuàng)建的任務(wù)。如果有多個 CronJob,它們相應(yīng)的任務(wù)總是允許并發(fā)執(zhí)行的。

掛起

?.spec.suspend?域也是可選的。如果設(shè)置為 ?true ?,后續(xù)發(fā)生的執(zhí)行都會掛起。 這個設(shè)置對已經(jīng)開始的執(zhí)行不起作用。默認是關(guān)閉的。

注意: 在調(diào)度時間內(nèi)掛起的執(zhí)行都會被統(tǒng)計為錯過的任務(wù)。當(dāng) ?.spec.suspend? 從 ?true ?改為 ?false ?時, 且沒有 開始的最后期限,錯過的任務(wù)會被立即調(diào)度。

任務(wù)歷史限制

?.spec.successfulJobsHistoryLimit? 和 ?.spec.failedJobsHistoryLimit?是可選的。 這兩個字段指定應(yīng)保留多少已完成和失敗的任務(wù)。 默認設(shè)置為3和1。限制設(shè)置為 ?0? 代表相應(yīng)類型的任務(wù)完成后不會保留。


以上內(nèi)容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號