控制结构(在模板语言中称为"actions")提供控制模板迭代流的能力。 Helm的模板语言提供了以下控制结构:

  • if/else, 用来创建条件语句
  • with, 用来指定范围
  • range, 提供"for each"类型的循环

除了这些之外,还提供了一些声明和使用命名模板的关键字:

  • define 在模板中声明一个新的命名模板
  • template 导入一个命名模板
  • block 声明一种特殊的可填充的模板块

一、If/Else

基本的条件结构:

{{ if PIPELINE }}
  # Do something
{{ else if OTHER PIPELINE }}
  # Do something else
{{ else }}
  # Default case
{{ end }}

注意我们讨论的是 管道 而不是值。这样做的原因是要清楚地说明控制结构可以执行整个管道,而不仅仅是计算一个值

如果是以下值时,管道会被设置为 false

  • 布尔false
  • 数字0
  • 空字符串
  • nil (空或null)
  • 空集合(map, slice, tuple, dict, array)

在所有其他条件下,条件都为true。

下面进行示例说明:

1.创建一个Chart

$ helm create helm-test

2.删掉系统自带的模板文件

[root@k8s-master01 ~]# rm -rf /root/helm-test/templates/*

3.新增模板文件,并填写Release.Name内置变量

[root@k8s-master01 ~]# vim /root/helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  drink: {{ .Values.favorite.drink | default "tea" | quote }}
  food: {{ .Values.favorite.food | upper | quote }}
  {{ if eq .Values.favorite.drink "coffee" }}mug: "true"{{ end }}

4.清空values.yaml文件,并添加以下内容

[root@k8s-master01 ~]# > /root/helm-test/values.yaml
[root@k8s-master01 ~]# vim /root/helm-test/values.yaml
favorite:
#  drink: coffee
  food: pizza

5.进行验证,观察到输出结果为tea

[root@k8s-master01 helm-test]# helm install aaa /root/helm-test/  --dry-run
NAME: aaa
LAST DEPLOYED: Sun Jul  9 17:35:31 2023
NAMESPACE: default
STATUS: pending-install
REVISION: 1
TEST SUITE: None
HOOKS:
MANIFEST:
---
# Source: helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: aaa-configmap
data:
  myvalue: "Hello World"
  drink: "tea"
  food: "PIZZA"

6.重新修改values.yaml文件,将drink: coffee前面的注释取消掉

[root@k8s-master01 ~]# vim /root/helm-test/values.yaml
favorite:
  drink: coffee
  food: pizza

7.重新进行验证,观察到输出结果为coffee

[root@k8s-master01 helm-test]# helm install aaa /root/helm-test/  --dry-run
NAME: aaa
LAST DEPLOYED: Sun Jul  9 17:35:00 2023
NAMESPACE: default
STATUS: pending-install
REVISION: 1
TEST SUITE: None
HOOKS:
MANIFEST:
---
# Source: helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: aaa-configmap
data:
  myvalue: "Hello World"
  drink: "coffee"
  food: "PIZZA"
  mug: "true"

二、控制空格

YAML认为空白是有意义的,因此管理空白变得很重要。Helm模板有些工具可以处理此类问题。

首先,模板声明的大括号语法可以通过特殊的字符修改,并通知模板引擎取消空白。{{-(包括添加的横杠和空格)表示向左删除空白, 而-}}表示右边的空格应该被去掉。 一定注意空格就是换行

1.创建一个Chart

$ helm create helm-test

2.删掉系统自带的模板文件

[root@k8s-master01 ~]# rm -rf /root/helm-test/templates/*

3.新增模板文件,并填写Release.Name内置变量

[root@k8s-master01 ~]# vim /root/helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  drink: {{ .Values.favorite.drink | default "tea" | quote }}
  food: {{ .Values.favorite.food | upper | quote }}
  {{ if eq .Values.favorite.drink "coffee" }}
  mug: "true"
  {{ end }}

4.清空values.yaml文件,并添加以下内容

[root@k8s-master01 ~]# > /root/helm-test/values.yaml
[root@k8s-master01 ~]# vim /root/helm-test/values.yaml
favorite:
  drink: coffee
  food: pizza

5.进行验证,观察到输出结果中存在空行

[root@k8s-master01 templates]# helm install aaa /root/helm-test/  --dry-run
NAME: aaa
LAST DEPLOYED: Sun Jul  9 17:47:08 2023
NAMESPACE: default
STATUS: pending-install
REVISION: 1
TEST SUITE: None
HOOKS:
MANIFEST:
---
# Source: helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: aaa-configmap
data:
  myvalue: "Hello World"
  drink: "coffee"
  food: "PIZZA"

  mug: "true"

6.重新修改configmap.yaml文件,添加-,{{-(包括添加的横杠和空格)表示向左删除空白

[root@k8s-master01 ~]# vim /root/helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  drink: {{ .Values.favorite.drink | default "tea" | quote }}
  food: {{ .Values.favorite.food | upper | quote }}
  {{- if eq .Values.favorite.drink "coffee" }}
  mug: "true"
  {{- end }}

当然你也可以使用

7.重新进行验证,观察到输出结果中空行已经消失

[root@k8s-master01 templates]# helm install aaa /root/helm-test/  --dry-run
NAME: aaa
LAST DEPLOYED: Sun Jul  9 17:51:19 2023
NAMESPACE: default
STATUS: pending-install
REVISION: 1
TEST SUITE: None
HOOKS:
MANIFEST:
---
# Source: helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: aaa-configmap
data:
  myvalue: "Hello World"
  drink: "coffee"
  food: "PIZZA"
  mug: "true"

三、修改使用with的范围

with操作一般来控制变量范围,.是对 当前作用域 的引用。因此 .Values就是告诉模板在当前作用域查找Values对象。

with的语法与if语句类似:

{{ with PIPELINE }}
  # restricted scope
{{ end }}

作用域可以被改变。with允许你为特定对象设定当前作用域(.)。比如,我们已经在使用.Values.favorite。 修改配置映射中的.的作用域指向.Values.favorite

apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  {{- end }}

注意:with后面的块只有在 PIPELINE 的值不为空时才会执行。

需要注意的是,在限定的作用域内,无法使用.访问父作用域的对象。错误示例如下:

  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  release: {{ .Release.Name }}
  {{- end }}

这样会报错因为Release.Name不在.限定的作用域内。但是如果对调最后两行就是正常的, 因为在{{ end }}之后作用域被重置了。

  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  {{- end }}
  release: {{ .Release.Name }}

或者可以使用$从父作用域中访问Release.Name对象。当模板开始执行后$会被映射到根作用域,且执行过程中不会更改

  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  release: {{ $.Release.Name }}
  {{- end }}

四、使用range操作循环

在Helm的模板语言中,在一个集合中迭代的方式是使用range操作符。

开始之前,我们先在values.yaml文件添加一个披萨的配料列表:

[root@k8s-master01 ~]# vim /root/helm-test/values.yaml
favorite:
  drink: coffee
  food: pizza
pizzaToppings:
  - mushrooms
  - cheese
  - peppers
  - onions

现在我们有了一个pizzaToppings列表(模板中称为切片)。修改模板把这个列表打印到配置映射中:

[root@k8s-master01 ~]# vim /root/helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  {{- end }}
  toppings: |-
    {{- range .Values.pizzaToppings }}
    - {{ . | title | quote }}
    {{- end }}

上面参数说明:

  • toppings: |-:声明的多行字符串

也可以使用$从父作用域访问Values.pizzaToppings列表。当模板开始执行后$会被映射到根作用域, 且执行过程中不会更改

[root@k8s-master01 ~]# vim /root/helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: {{ .Release.Name }}-configmap
data:
  myvalue: "Hello World"
  {{- with .Values.favorite }}
  drink: {{ .drink | default "tea" | quote }}
  food: {{ .food | upper | quote }}
  toppings: |-
    {{- range $.Values.pizzaToppings }}
    - {{ . | title | quote }}
    {{- end }}
  {{- end }}

进行验证,观察到输出结果

[root@k8s-master01 templates]# helm install aaa /root/helm-test/  --dry-run
NAME: aaa
LAST DEPLOYED: Sun Jul  9 18:12:15 2023
NAMESPACE: default
STATUS: pending-install
REVISION: 1
TEST SUITE: None
HOOKS:
MANIFEST:
---
# Source: helm-test/templates/configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: aaa-configmap
data:
  myvalue: "Hello World"
  drink: "coffee"
  food: "PIZZA"
  toppings: |-
    - "Mushrooms"
    - "Cheese"
    - "Peppers"
    - "Onions"