搭出 chart 骨架并打上标准标签
目标
亲手创建 Helm chart 的标准结构,在一个位置管理名称与 label,使所有 object 都带上一致的标准 label。
为什么重要
学习 chart 时,人们往往先关心 template 语法,但真正决定 chart 生命周期的是结构。Chart.yaml 负责说明这组内容是什么,values.yaml 负责说明用户能调整什么,templates/ 负责将这些值呈现为什么形态。只有这样分离,才能消除“为每个环境复制文件再修改”的习惯。label 也不是偏好问题。app.kubernetes.io/* 是 Kubernetes 官方推荐标准,管理工具与 dashboard 会据此聚合 resource。尤其要注意:common label 与 selector label 必须分离。Deployment 的 spec.selector 创建后不可更改,而 common label 混有 chart version 与 app version;若直接用于 selector,升级版本时就会被拒绝。
步骤
- 在
/root/helm/lab/labhub-web创建 chart scaffold(可执行helm create labhub-web,运行目录为/root/helm/lab)。必须包含Chart.yaml、values.yaml、.helmignore三个文件、至少含 3 个文件的templates/,以及charts/目录。另请预先创建产物目录/root/helm/lab/out。 - 填写
/root/helm/lab/labhub-web/Chart.yaml。必须包含apiVersion: v2、name: labhub-web、type: application、SemVerversion(如0.1.0)、appVersion: "1.27",以及一行description。 - 将
/root/helm/lab/labhub-web/values.yaml默认值设为:replicaCount: 2、image.repository: nginx、image.tag: "1.27"、image.pullPolicy: IfNotPresent、service.port: 80。文件中至少要有一行以#开头的 comment。 /root/helm/lab/labhub-web/templates/_helpers.tpl中必须定义labhub-web.fullname、labhub-web.labels、labhub-web.selectorLabels,名称生成处必须包含trunc 63。/root/helm/lab/labhub-web/templates/deployment.yaml必须以include "labhub-web...形式调用这些定义。- 用
helm template labhub-web /root/helm/lab/labhub-web > /root/helm/lab/out/rendered.yaml保存 render 结果。结果至少包含 2 个 object;Deployment 的metadata.labels必须包含app.kubernetes.io/managed-by: Helm、app.kubernetes.io/name: labhub-web、app.kubernetes.io/version,Service 的metadata.labels也必须带有同样的 common label。 - 让
/root/helm/lab/labhub-web/templates/NOTES.txt至少各引用一个以.Release.Name和.Values.开头的值,并将实际 render 后的说明保存到/root/helm/lab/out/notes.txt。可从helm install labhub-web /root/helm/lab/labhub-web --dry-run输出中截取NOTES:以下部分(sed -n '/^NOTES:/,$p')。保存文件必须包含labhub-web,且不能残留未 render 的花括号语法。 - 使用
helm lint /root/helm/lab/labhub-web > /root/helm/lab/out/lint.txt保存 lint 结果。文件必须包含 lint summary 行,且不能出现任何[ERROR]。 - 用
helm template labhub-web /root/helm/lab/labhub-web --set replicaCount=5 > /root/helm/lab/out/scaled.yaml保存 override value 后的 render。最终确认四点:/root/helm/lab/out/rendered.yaml中 Deployment 的spec.replicas为 2;/root/helm/lab/out/scaled.yaml中为 5;container image 为nginx:1.27;Service 首个 port 为 80。此外,Servicespec.selector中的app.kubernetes.io/name必须与 Deployment Pod template label 的app.kubernetes.io/name相同。
参考
- 每次实验都会启动新的 Pod,其他实验创建的 chart 或 release 不会保留。所需 chart 每次都从头创建,这正体现 chart 是可复现 package。
- scaffold 命令生成的默认 chart 已包含 helper 和标准 label。调整值与名称通常比删除后重写更快。
helm template无需 cluster 即可运行;helm install --dry-run不会在 cluster 创建任何内容,同时会显示 NOTES,检查说明时需要后者。- 常见错误 1:保持原有
appVersion。image tag 默认值和app.kubernetes.io/versionlabel 都源于此处,会导致值不一致。 - 常见错误 2:直接复制
NOTES.txt原文保存为/root/helm/lab/out/notes.txt。这会残留花括号,被判定为并非 render 结果。
创建 chart scaffold
在 /root/helm/lab/labhub-web 创建 chart scaffold(可执行 helm create labhub-web,运行目录为 /root/helm/lab)。必须包含 Chart.yaml、values.yaml、.helmignore 三个文件、至少含 3 个文件的 templates/,以及 charts/ 目录。另请预先创建产物目录 /root/helm/lab/out。
Helm 提供了一条命令可一次生成标准结构。生成后确认 Chart.yaml、values.yaml、.helmignore、templates/、charts/ 五处都存在;charts/ 即使为空也必须存在。
填写 Chart.yaml 身份信息
填写 /root/helm/lab/labhub-web/Chart.yaml。必须包含 apiVersion: v2、name: labhub-web、type: application、SemVer version(如 0.1.0)、appVersion: "1.27",以及一行 description。
Helm 3 的 apiVersion 是固定的。还要注意 chart 自身 version 与 app version 是不同字段,请思考哪一个应与 image tag 对齐。
设计 values.yaml 默认值
将 /root/helm/lab/labhub-web/values.yaml 默认值设为:replicaCount: 2、image.repository: nginx、image.tag: "1.27"、image.pullPolicy: IfNotPresent、service.port: 80。文件中至少要有一行以 # 开头的 comment。
相关值不要全部平铺,而要像 image 一样分组。values.yaml 是用户会阅读的唯一文档,因此至少应有一条 comment。
用 helper 提取名称与 label
/root/helm/lab/labhub-web/templates/_helpers.tpl 中必须定义 labhub-web.fullname、labhub-web.labels、labhub-web.selectorLabels,名称生成处必须包含 trunc 63。/root/helm/lab/labhub-web/templates/deployment.yaml 必须以 include "labhub-web... 形式调用这些定义。
以下划线开头的 template 文件不会 render 成 manifest。请思考为何 common label 与 selector label 必须分别定义。名称还需要长度限制处理。
为所有 object 添加标准 label
用 helm template labhub-web /root/helm/lab/labhub-web > /root/helm/lab/out/rendered.yaml 保存 render 结果。结果至少包含 2 个 object;Deployment 的 metadata.labels 必须包含 app.kubernetes.io/managed-by: Helm、app.kubernetes.io/name: labhub-web、app.kubernetes.io/version,Service 的 metadata.labels 也必须带有同样的 common label。
Deployment 与 Service 都必须带有同样的 common label。managed-by 值不要手写,应从 release 信息取得。评分器会检查已保存的 render 文件。
编写并 render 安装说明
让 /root/helm/lab/labhub-web/templates/NOTES.txt 至少各引用一个以 .Release.Name 和 .Values. 开头的值,并将实际 render 后的说明保存到 /root/helm/lab/out/notes.txt。可从 helm install labhub-web /root/helm/lab/labhub-web --dry-run 输出中截取 NOTES: 以下部分(sed -n '/^NOTES:/,$p')。保存文件必须包含 labhub-web,且不能残留未 render 的花括号语法。
NOTES.txt 也是 template。应同时使用 release name 与 values 值,让用户知道安装了什么。保存文件必须是 render 结果,不能残留花括号。
通过 chart lint
使用 helm lint /root/helm/lab/labhub-web > /root/helm/lab/out/lint.txt 保存 lint 结果。文件必须包含 lint summary 行,且不能出现任何 [ERROR]。
将完整 lint 输出保存到文件。只要有一个 ERROR 就会失败;warning 虽可通过,也应阅读原因。
验证 render 结果
用 helm template labhub-web /root/helm/lab/labhub-web --set replicaCount=5 > /root/helm/lab/out/scaled.yaml 保存 override value 后的 render。最终确认四点:/root/helm/lab/out/rendered.yaml 中 Deployment 的 spec.replicas 为 2;/root/helm/lab/out/scaled.yaml 中为 5;container image 为 nginx:1.27;Service 首个 port 为 80。此外,Service spec.selector 中的 app.kubernetes.io/name 必须与 Deployment Pod template label 的 app.kubernetes.io/name 相同。
需要默认 render 与 override value 后的 render 两份结果。还要亲自核对 Service selector 与 Pod template label 的 key/value 是否相同;否则流量无法到达 Pod。