验证 helm 图表内容

问题描述 投票:0回答:4

我正在开发一个图表,但其中有一个错误 -

imagePullSecrets
属性放置不正确。当我尝试通过

安装它时
helm install ./mychart

放错位置的元素被简单地忽略了,我想知道出了什么问题。

当我这么做的时候

helm template ./mychart | kubectl apply --dry-run -f -

它改为打印:

error: error validating "STDIN": error validating data: ValidationError(Deployment.spec.template.spec.containers[0]): unknown field "imagePullSecrets" in io.k8s.api.core.v1.Container

这清楚地表明出了什么问题。我不确定它是否与耕耘机对扩展模板的实际作用相匹配。

但是如果我只是做一个

helm install --dry-run --debug ./mychart

它只是显示展开的模板,看起来还不错。

那么如何正确验证我的所有模板是否与 helm 对应的模式匹配?

debugging kubernetes kubernetes-helm
4个回答
26
投票

您可以通过

helm lint ./mychart
对图表进行 lint,如果发现问题,应该打印以下内容:

$ helm lint ./mychart
==> Linting ./mychart
[ERROR] Chart.yaml: version is required
[INFO] Chart.yaml: icon is recommended

Error: 1 chart(s) linted, 1 chart(s) failed

参见头盔棉绒


18
投票

使用kubeconform

helm template ./mychart | kubeconform -strict

如果您有 CRD,您可能需要使用

kubeconform -ignore-missing-schemas
。我建议提供架构版本:
kubeconform -kubernetes-version 1.18

建议:专门化你的图表并验证它们。示例如下。

简单:

helm template --set some.key="val" | kubeconform -strict

复杂:

VALUES_FILE=$(cat << EOF
some:
  key: "val"

another:
  key:
    another: "val"
EOF
)
# It is important to quote "$VALUES_FILE" to ensure line breaks and indentation are preserved
echo "$VALUES_FILE" | helm template -f - | kubeconform -strict

6
投票

为了避免 Helm Chart 安装失败,我建议在本地或/和 CI 管道中遵循以下顺序:

如果 linter 遇到会导致图表失败的事情 安装时,它会发出[ERROR]消息。

  • 运行helm template,测试图表是否能成功本地渲染。虽然一旦发生 helm->kubernetes api 服务器交互,安装仍然可能失败,但它仍然提供良好的质量检查。

  • 渲染图表后,使用

    kubeval
    (不支持 CRD)或
    kubeconform
    (支持 CRD)验证图表的 Kubernetes 清单是否符合 Kubernetes 架构:

helm template [chart_name] . | kubeval

  • 运行 helm 单元测试,以验证图表值是否符合预期(例如,副本数为 1,卷的类型为
    hostPath
    ,等等):

helm unittest [chart_name] [chart_name]

我在博客中总结了如何测试 Helm Charts


5
投票

我强烈建议使用以下 2 种解决方案的组合

解决方案1

使用values.schema.json在values.yaml文件上强加一个结构。

示例:

{
  "$schema": "https://json-schema.org/draft-07/schema#",
  "properties": {
    "image": {
      "description": "Container Image",
      "properties": {
        "repo": {
          "type": "string"
        },
        "tag": {
          "type": "string"
        }
      },
      "type": "object"
    },
    "name": {
      "description": "Service name",
      "type": "string"
    },
    "port": {
      "description": "Port",
      "minimum": 0,
      "type": "integer"
    },
    "protocol": {
      "type": "string"
    }
  },
  "required": [
    "protocol",
    "port"
  ],
  "title": "Values",
  "type": "object"
}

(!) 此模式将应用于值以对其进行验证。调用以下任何命令时都会发生验证:

helm install
helm upgrade
helm lint
helm template

为了向验证添加条件 - 请阅读此处

(*) 进一步阅读:好文章

解决方案2

在某些情况下,使用条件时

values.schema.json
中的代码可能可读性较差,或者我们希望在验证中使用更动态的逻辑。

在这种情况下,我们可以创建一个

validations.yaml
文件(有些供应商更喜欢使用
.tpl
文件)并使用 go templates 添加验证逻辑。

示例:

如果特定功能(启用后)需要 IP 或 DNS:

  some_feature:
    enabled: true
    ip:
    dns:

验证逻辑可以显式编写:

{{- if .Values.some_feature.enabled -}}
    {{- if and (not .Values.some_feature.ip ) (not .Values.some_feature.dns  ) -}}
        When some_feature is enabled, ip or dns must be given.
    {{- end -}}
{{- end -}}

(*) 这个逻辑也可以使用 json-schema if-else 语句 来编写,但可能可读性较差。

(**) 考虑将所有验证放在

/tests
/validations
文件夹下,其中所有测试都分为单独的文件(如单元测试)。

© www.soinside.com 2019 - 2024. All rights reserved.