天天看點

簡化Kubernetes應用部署工具-Helm之Release配置

本文講的是<b>簡化Kubernetes應用部署工具-Helm之Release配置</b>【編者的話】微服務和容器化給複雜應用部署與管理帶來了極大的挑戰。Helm是目前Kubernetes服務編排領域的唯一開源子項目,做為Kubernetes應用的一個包管理工具,可了解為Kubernetes的apt-get / yum,由Deis 公司發起,該公司已經被微軟收購。Helm通過軟體打包的形式,支援釋出的版本管理和控制,很大程度上簡化了Kubernetes應用部署和管理的複雜性。

随着業務容器化與向微服務架構轉變,通過分解巨大的單體應用為多個服務的方式,分解了單體應用的複雜性,使每個微服務都可以獨立部署和擴充,實作了靈活開發和快速疊代和部署。但任何事情都有兩面性,雖然微服務給我們帶來了很多便利,但由于應用被拆分成多個元件,導緻服務數量大幅增加,對于Kubernetest編排來說,每個元件有自己的資源檔案,并且可以獨立的部署與伸縮,這給采用Kubernetes做應用編排帶來了諸多挑戰:

管理、編輯與更新大量的K8s配置檔案

部署一個含有大量配置檔案的複雜K8s應用

分享和複用K8s配置和應用

參數化配置模闆支援多個環境

管理應用的釋出:復原、diff和檢視釋出曆史

控制一個部署周期中的某一些環節

釋出後的驗證

而采用Helm,可以輕松的解決上面的問題。

Helm把Kubernetes資源(比如deployments、services或 ingress等) 打包到一個chart中,而chart被儲存到chart倉庫。通過chart倉庫可用來存儲和分享chart。Helm使釋出可配置,支援釋出應用配置的版本管理,簡化了Kubernetes部署應用的版本控制、打包、釋出、删除、更新等操作。

本文的目标是展示Helm如何做應用配置管理以及服務依賴的處理。

關于Helm安裝、簡介以及使用請參考:

<a href="http://dockone.io/article/2702">簡化Kubernetes應用部署工具-Helm安裝</a>

<a href="http://dockone.io/article/2701">簡化Kubernetes應用部署工具-Helm簡介</a>

<a href="http://dockone.io/article/2703">簡化Kubernetes應用部署工具-Helm之應用部署</a>

Helm Chart模闆采用go模闆語言編寫 Go template language,模闆的值記錄在values.yaml檔案中。values.yaml檔案中的值可以在安裝chart過程中,通過參數–values YAML_FILE_PATH或–set key1=value1, key2=value2替換。

注意:模闆語言中的引用數值型需要注意,不加引号,會被解釋為數值。

建立自定義chart

檢視mychart結構:

生成chart目錄裡有Chart.yaml, values.yaml and NOTES.txt等檔案,下面分别對chart中幾個重要檔案解釋:

Chart.yaml 包含了chart的metadata,描述了Chart名稱、描述資訊與版本。

values.yaml:存儲了模闆檔案變量。

templates/:記錄了全部模闆檔案。

charts/:依賴chart存儲路徑。

其中mychart/templates/的檔案及其作用如下:

NOTES.txt:給出了部署chart後的幫助文檔,例如如何使用chart、列出預設的設定等。

deployment.yaml:建立 Kubernetes deployment的yaml檔案。

service.yaml:建立deployment的service endpoint yams檔案。

_helpers.tpl: 模闆使用幫助檔案。

建立mychart/templates/configmap.yaml檔案,内容如下:

一個模闆指令由{{}}标記。{{ .Release.Name }}會把release name插入模闆。傳入模闆的值可被認作是namespaces對象,通過”.”來分隔namespaces元素。

對象通過模闆引擎傳給模闆,有幾種方式在模闆内建立新的對象,比如後面要講到的tuple。

上面章節提到Helm模闆提供了内置的對象,而Values做為4個内置對象之一,有4種來源:

可通過chart中的values.yaml檔案

對于subchart,父chart中values.yaml檔案

helm install 或 helm update 指定 -f flag (helm install -f myvals.yaml ./mychart)

通過--set 參數傳值(例如 helm install --set foo=bar ./mychart)

說明:values.yaml預設會被引用,但其會被父chart中的values.yaml檔案内容覆寫(overridden),而父chart中的values.yaml檔案會被戶用-f指定的檔案内容覆寫,而使用者用-f指定的檔案會被–set參數傳的值覆寫。簡單的說,也就是上面4種Values來源的重要性由上到下的順序,優先級由低到高。

如需要删除鍵值對中删除預設key,需要将key的值設定為null, helm也會将從覆寫的鍵值對中将其剔除。舉例說明,期望将下面例子中的livenessProbe替換為 exec

在helm install 時,使用–set livenessProbe.exec.command=[cat,docroot/CHANGELOG.txt],結果如下:

這并非我們的預期,而通過将livenessProbe.httpGet指派為null:

前面展示的模闆例子中,模闆内容基本不去修改,但有一些情況下,我們希望提供給模闆的資料對我們更加簡單易用。例如對于 .Values對象注入模闆的鍵值可利用模闆提供的 quote功能引用。

Helm 提供了超過60功能函數,其中一些定義在Go模闆語言自身: Go template language . 這些函數是 Sprig template library的一部分。

Pipelines是模闆語言的非常強大的特性之一,與Linux/Unix的pipeline類似,pipelines是把模闆語言的多個指令通過 (|)的分隔形式,以描述的順序的實作指令聚合功能。

上面例子中,對.Values.favorite.drink | repeat 5 | quote的值coffee重複了5次後引用,而對.Values.favorite.food先做了一次大寫轉換然後加以引用。類似結果如下:

使用 DEFAULT功能

default是模闆中經常使用一個功能,該功能是在模闆中指定一個預設值。例如下面例子中,如果.Values.favorite.drink沒有被指派,那麼模闆被引用時,tea便為其預設值。

對于Helm模闆,類似eq, ne, lt, gt, and, or等操作符已經實作為函數,

Helm模闆語言提供了如下控制結構:

if/else 條件語句

with 指定範圍

range, 提供了“for each”-形式的循環

除此之外,Helm還提供了一些命名模闆的行為:

define 模闆内部定義一個命名模闆

template 導入一個命名模闆

block declares a special kind of fillable template area

條件基本的控制結構如下:

pipeline會被認為是false 如果值是下面幾種類型:

布爾類型 false

數字 0

空串

nil (empty or null)

空集合 (map, slice, tuple, dict, array)

下面configmap例子中,mug預期結果為true:

執行helm install --dry-run --debug mychart指令:

Helm模闆語言對空格非常敏感,左側有{{-(破折号後面有一個空格)表明空格需要被移除,而右側 -}}表示空格會被消費。

如果不加-,舉例如下:

那麼輸出時會移除 {{ 與 }}而留下空格:

或者:

結果如下,因為-}}已經把其所在的行移除了。

food: "PIZZA"mug:true

通過 with 與(.) 指定目前範圍到某一個指定的對象,例如下面例子中 .Values.favorites,後面再引用drink與food 時,無需再指定Values.favorite

像多數程式設計語言支援 for 與 foreach 等循環一樣,Helm模闆語言通過支援range操作符周遊一個集合。

下面例子中 values.yaml 檔案部分内容如下:

在ConfigMap中需要周遊Values.pizzaToppings的全部值,可以采用下面形式:

其中 |-的作用是生成一個占用多行的字元串。

另外Helm提供了 tuple函數,可以在模闆内建立一個list并且周遊它。例如:

結果如下:

模闆變量在 range的循環中非常有用,變量的定義格式為$name ,可通過 :=指派。舉例如下:

每循環一次 $index的值從0開始遞增,并且将周遊的值賦給$topping

或者,對應存在鍵值對的對象,可以用 range擷取:

Helm允許我們建立一個命名模闆,通過模闆名稱,可以在任何地方引用它。一般情況下命名模闆會寫在_helpers.tpl 中,并以形式 ({{/* ... */}})加上模闆說明。比如下面例子中定義了一個my_labels命名模闆,并且用 include通過 {{- include "my_labels" }}嵌入到configmap的metadata中。通常 include也可以用 template代替,但是 include在處理YAML檔案的格式輸出上會更勝一籌,另外 include可以包含一個變量的模闆{{ include $mytemplate }}。

在configmap.yaml檔案中引用該命名模闆:

需要注意的是,命名模闆名稱是全局的,如果存在多個同名的模闆,最後被load到Tiller中的模闆會被最終使用。另外模闆的命名通常以chart的名字做為字首,比如 {{ define "mychart.labels" }} 或 {{ define "mychart_labels" }}。

前面的命名模闆中,并沒有使用模闆的内置對象。下面例子中在命名模闆中使用了内置對象:

在configmap中消費這個命名模闆,注意在命名模闆調用的末尾加上 ., indent 2表示引用的模闆内容向右縮進2格。

上個章節中展示了幾種建立和通路命名模闆的方式,通過命名模闆,可以很容易在一個模闆中引用另外一個模闆。但有的時候,我們還有導入一個普通檔案内容來渲染模闆的需求,而不僅僅是以模闆的形式。Helm提供了一個内置 .Files對象。

Helm支援chart中存在一個普通類型的檔案,這些檔案也會被與其他模闆檔案一同打包發給給Tiller,但檔案大小目前被限制在1M以内。由于安全原因,一般情況下 templates/的.Files對象不可通路,另外,chart并不會保留 UNIX mode的資訊,檔案層面的權限并不會影響對.Files對象的通路控制。

在 chart install 或 chart upgrade的尾部,會列印出使用者幫助資訊,該資訊在 templates/NOTES.txt中定制。Helm并不強制提供使用者幫助資訊,但為了使用者更加友善了解和使用所安裝的應用,強烈建議在templates/NOTES.txt加上使用者幫助資訊。舉例如下:

所謂subchart,指的是一個chart依賴其他chart,被依賴的chart即被稱為subchart。

關于subchart的幾點說明:

subchart無需依賴父chart,其是一個完全獨立操作的chart,擁有自己values和模闆。

subchart沒權限通路父chart的values,但父chart可以覆寫subchart的values。

無論subchart或父chart都可以通路helm全局values。

建立subchart的過程與普通chart基本一緻,唯一需要注意的是,subchart需要建立在父chart的charts檔案夾内,舉例如下:

為sub chart添加模闆和values:

添加 values.yaml 到 mychart/charts/mysubchart :

在 mychart/charts/mysubchart/templates/configmap.yaml 中建立ConfigMap模闆:

subchart可以單獨安裝:

父chart的values可以覆寫子chart,在mychart/values.yaml添加:

然後執行 helm install --dry-run --debug mychart指令:

從結果可知,子chart的dessert的已由cake被替換為ice cream。

全部chart,包括子chart都可以通路全局chart values。一般全局chart values記錄在父chart Values.global中。以mychart/values.yaml為例:

那麼在mysubchart/templates/configmap.yaml 中,即可以通過 .Values.global.salad 通路:

Helm中父子chart之間可以共享模闆,在任何一個chart中定義的塊,對其他chart均可通路。

模闆在Tiller server端渲染,而非Helm client端。經過Tiller server渲染的模闆,最後發送給Kubernetes API server,而YAML檔案除了格式問題外,可能還有其他多種因為會被Kubernetes API server拒絕。

helm lint 驗證chart是否遵循了一些好的實踐

helm install --dry-run --debug: chart發送給Tiller server并用value.yaml中的值來渲染相關模闆。但實際上chart并沒有安裝, 隻是輸出了渲染後的模闆。

helm get manifest: 檢視Tiller server端已安裝的模闆。

歡迎轉載,請注明作者出處:張夏,FreeWheel Lead Engineer,DockOne社群

原文釋出時間為:2017-09-14

本文來自雲栖社群合作夥伴Dockerone.io,了解相關資訊可以關注Dockerone.io。

原文标題:簡化Kubernetes應用部署工具-Helm之Release配置

繼續閱讀