新聞中心
使用展開的方式進行并行處理
本任務(wù)展示基于一個公共的模板運行多個Jobs。 你可以用這種方法來并行執(zhí)行批處理任務(wù)。

創(chuàng)新互聯(lián)-專業(yè)網(wǎng)站定制、快速模板網(wǎng)站建設(shè)、高性價比郊區(qū)網(wǎng)站開發(fā)、企業(yè)建站全套包干低至880元,成熟完善的模板庫,直接使用。一站式郊區(qū)網(wǎng)站制作公司更省心,省錢,快速模板網(wǎng)站建設(shè)找我們,業(yè)務(wù)覆蓋郊區(qū)地區(qū)。費用合理售后完善,十載實體公司更值得信賴。
在本任務(wù)示例中,只有三個工作條目:apple、banana 和 cherry。 示例任務(wù)處理每個條目時打印一個字符串之后結(jié)束。
在開始之前
你應(yīng)先熟悉基本的、非并行的 Job 的用法。
你必須擁有一個 Kubernetes 的集群,同時你的 Kubernetes 集群必須帶有 kubectl 命令行工具。 建議在至少有兩個節(jié)點的集群上運行本教程,且這些節(jié)點不作為控制平面主機。 如果你還沒有集群,你可以通過 Minikube 構(gòu)建一個你自己的集群,或者你可以使用下面任意一個 Kubernetes 工具構(gòu)建:
- Katacoda
- 玩轉(zhuǎn) Kubernetes
任務(wù)中的基本模板示例要求安裝命令行工具 ?sed?。 要使用較高級的模板示例,你需要安裝 Python, 并且要安裝 Jinja2 模板庫。
一旦 Python 已經(jīng)安裝好,你可以運行下面的命令安裝 Jinja2:
pip install --user jinja2
基于模板創(chuàng)建 Job
首先,將以下作業(yè)模板下載到名為 ?job-tmpl.yaml? 的文件中。
apiVersion: batch/v1
kind: Job
metadata:
name: process-item-$ITEM
labels:
jobgroup: jobexample
spec:
template:
metadata:
name: jobexample
labels:
jobgroup: jobexample
spec:
containers:
- name: c
image: busybox:1.28
command: ["sh", "-c", "echo Processing item $ITEM && sleep 5"]
restartPolicy: Never
# 使用 curl 下載 job-tmpl.yaml
curl -L -s -O https://K8S.io/examples/application/job/job-tmpl.yaml你所下載的文件不是一個合法的 Kubernetes 清單。 這里的模板只是 Job 對象的 yaml 表示,其中包含一些占位符,在使用它之前需要被填充。 ?$ITEM? 語法對 Kubernetes 沒有意義。
基于模板創(chuàng)建清單
下面的 Shell 代碼片段使用 ?sed ?將字符串 ?$ITEM? 替換為循環(huán)變量,并將結(jié)果 寫入到一個名為 ?jobs ?的臨時目錄。
# 展開模板文件到多個文件中,每個文件對應(yīng)一個要處理的條目
mkdir ./jobs
for i in apple banana cherry
do
cat job-tmpl.yaml | sed "s/\$ITEM/$i/" > ./jobs/job-$i.yaml
done檢查上述腳本的輸出:
ls jobs/
輸出類似于:
job-apple.yaml
job-banana.yaml
job-cherry.yaml你可以使用任何一種模板語言(例如:Jinja2、ERB),或者編寫一個程序來 生成 Job 清單。
基于清單創(chuàng)建 Job
接下來用一個 kubectl 命令創(chuàng)建所有的 Job:
kubectl create -f ./jobs
輸出類似于:
job.batch/process-item-apple created
job.batch/process-item-banana created
job.batch/process-item-cherry created現(xiàn)在檢查 Job:
kubectl get jobs -l jobgroup=jobexample
輸出類似于:
NAME COMPLETIONS DURATION AGE
process-item-apple 1/1 14s 22s
process-item-banana 1/1 12s 21s
process-item-cherry 1/1 12s 20s使用 kubectl 的 ?-l? 選項可以僅選擇屬于當前 Job 組的對象 (系統(tǒng)中可能存在其他不相關(guān)的 Job)。
你可以使用相同的 標簽選擇算符 來過濾 Pods:
kubectl get pods -l jobgroup=jobexample
輸出類似于:
NAME READY STATUS RESTARTS AGE
process-item-apple-kixwv 0/1 Completed 0 4m
process-item-banana-wrsf7 0/1 Completed 0 4m
process-item-cherry-dnfu9 0/1 Completed 0 4m我們可以用下面的命令查看所有 Job 的輸出:
kubectl logs -f -l jobgroup=jobexample
輸出類似于:
Processing item apple
Processing item banana
Processing item cherry清理
# 刪除所創(chuàng)建的 Job
# 集群會自動清理 Job 對應(yīng)的 Pod
kubectl delete job -l jobgroup=jobexample使用高級模板參數(shù)
在第一個例子中,模板的每個示例都有一個參數(shù) 而該參數(shù)也用在 Job 名稱中。不過,對象 名稱 被限制只能使用某些字符。
這里的略微復(fù)雜的例子使用 Jinja 模板語言 來生成清單,并基于清單來生成對象,每個 Job 都有多個參數(shù)。
在本任務(wù)中,你將會使用一個一行的 Python 腳本,將模板轉(zhuǎn)換為一組清單文件。
首先,復(fù)制下面的 Job 對象模板到一個名為 ?job.yaml.jinja2? 的文件。
{% set params = [{ "name": "apple", "url": "http://dbpedia.org/resource/Apple", },
{ "name": "banana", "url": "http://dbpedia.org/resource/Banana", },
{ "name": "cherry", "url": "http://dbpedia.org/resource/Cherry" }]
%}
{% for p in params %}
{% set name = p["name"] %}
{% set url = p["url"] %}
---
apiVersion: batch/v1
kind: Job
metadata:
name: jobexample-{{ name }}
labels:
jobgroup: jobexample
spec:
template:
metadata:
name: jobexample
labels:
jobgroup: jobexample
spec:
containers:
- name: c
image: busybox:1.28
command: ["sh", "-c", "echo Processing URL {{ url }} && sleep 5"]
restartPolicy: Never
{% endfor %}上面的模板使用 python 字典列表(第 1-4 行)定義每個作業(yè)對象的參數(shù)。 然后使用 for 循環(huán)為每組參數(shù)(剩余行)生成一個作業(yè) yaml 對象。 我們利用了多個 YAML 文檔(這里的 Kubernetes 清單)可以用 ?---? 分隔符連接的事實。 我們可以將輸出直接傳遞給 kubectl 來創(chuàng)建對象。
接下來我們用單行的 Python 程序?qū)⒛0逭归_。
alias render_template='python -c "from jinja2 import Template; import sys; print(Template(sys.stdin.read()).render());"'
使用 ?render_template ?將參數(shù)和模板轉(zhuǎn)換成一個 YAML 文件,其中包含 Kubernetes 資源清單:
# 此命令需要之前定義的別名
cat job.yaml.jinja2 | render_template > jobs.yaml你可以查看 ?jobs.yaml? 以驗證 ?render_template ?腳本是否正常工作。
當你對輸出結(jié)果比較滿意時,可以用管道將其輸出發(fā)送給 kubectl,如下所示:
cat job.yaml.jinja2 | render_template | kubectl apply -f -
Kubernetes 接收清單文件并執(zhí)行你所創(chuàng)建的 Job。
清理
# 刪除所創(chuàng)建的 Job
# 集群會自動清理 Job 對應(yīng)的 Pod
kubectl delete job -l jobgroup=jobexample在真實負載中使用 Job
在真實的負載中,每個 Job 都會執(zhí)行一些重要的計算,例如渲染電影的一幀, 或者處理數(shù)據(jù)庫中的若干行。這時,?$ITEM? 參數(shù)將指定幀號或行范圍。
在此任務(wù)中,你運行一個命令通過取回 Pod 的日志來收集其輸出。 在真實應(yīng)用場景中,Job 的每個 Pod 都會在結(jié)束之前將其輸出寫入到某持久性存儲中。 你可以為每個 Job 指定 PersistentVolume 卷,或者使用其他外部存儲服務(wù)。 例如,如果你在渲染視頻幀,你可能會使用 HTTP 協(xié)議將渲染完的幀數(shù)據(jù) 用 'PUT' 請求發(fā)送到某 URL,每個幀使用不同的 URl。
Job 和 Pod 上的標簽
你創(chuàng)建了 Job 之后,Kubernetes 自動為 Job 的 Pod 添加 標簽,以便能夠?qū)⒁粋€ Job 的 Pod 與另一個 Job 的 Pod 區(qū)分開來。
在本例中,每個 Job 及其 Pod 模板有一個標簽: ?jobgroup=jobexample?。
Kubernetes 自身對標簽名 ?jobgroup ?沒有什么要求。 為創(chuàng)建自同一模板的所有 Job 使用同一標簽使得我們可以方便地同時操作組中的所有作業(yè)。 在第一個例子中,你使用模板來創(chuàng)建了若干 Job。 模板確保每個 Pod 都能夠獲得相同的標簽,這樣你可以用一條命令檢查這些模板化 Job 所生成的全部 Pod。
說明: 標簽鍵 ?
jobgroup?沒什么特殊的,也不是保留字。 你可以選擇你自己的標簽方案。
替代方案
如果你有計劃創(chuàng)建大量 Job 對象,你可能會發(fā)現(xiàn):
- 即使使用標簽,管理這么多 Job 對象也很麻煩。
- 如果你一次性創(chuàng)建很多 Job,很可能會給 Kubernetes 控制面帶來很大壓力。 一種替代方案是,Kubernetes API 可能對請求施加速率限制,通過 429 返回 狀態(tài)值臨時拒絕你的請求。
- 你可能會受到 Job 相關(guān)的資源配額 限制:如果你在一個批量請求中觸發(fā)了太多的任務(wù),API 服務(wù)器會永久性地拒絕你的某些請求。
還有一些其他作業(yè)模式 可供選擇,這些模式都能用來處理大量任務(wù)而又不會創(chuàng)建過多的 Job 對象。
你也可以考慮編寫自己的控制器 來自動管理 Job 對象。
當前名稱:創(chuàng)新互聯(lián)kubernetes教程:Kubernetes使用展開的方式進行并行處理
本文URL:http://fisionsoft.com.cn/article/dhpiecs.html


咨詢
建站咨詢
