- 云原生
- 运维
- 工具
【免费下载链接】helmfile
Declaratively deploy your Kubernetes manifests, Kustomize configs, and Charts as Helm releases. Generate all-in-one manifests for use with ArgoCD.
本文基于 helmfile 官方文档 docs/advanced-features.md 展开,系统讲解 helmfile 的五大高级能力:基于 Kubedog 的精细化资源跟踪(trackMode全参数族)、借助 vals 导入外部配置参数、以 Helm 方式部署 Kustomization、对 Helm Chart 进行 Adhoc Kustomize 改造、以及不 fork Chart 直接注入依赖与按环境拆分 Lockfile。读完本文,你将能在apply/sync时获得远超 Helm 内置--wait的部署反馈,并能把 kustomization、Chart 与补丁统一纳入声明式发布体系。
一、使用 Kubedog 进行资源跟踪
Helmfile 可以借助 werf/kubedog 这类高级跟踪库替代 Helm 内置的--wait标志,从而获得更详细的部署进度反馈与更强的控制能力。其核心思想是:不再让 Helm 黑盒等待,而是由 Helmfile 直接观察目标资源的就绪状态,并实时输出进度与日志。
在 pkg/state/state.go 中,ReleaseSpec声明了完整的跟踪相关字段(TrackMode、TrackTimeout、TrackLogs、TrackLogsInterval、TrackLogsUntilReady、TrackFailedLogs、TrackKinds、SkipKinds、TrackResources、KubedogQPS、KubedogBurst等),全部以track*/kubedog*前缀出现在releases[]下,与命令行 flag 一一对应。
1.1 基本用法
在helmfile.yaml中启用 kubedog 跟踪:
releases: - name: myapp chart: ./charts/myapp trackMode: kubedog trackTimeout: 300 # 秒 trackLogs: true也可以在命令行上临时指定(优先级高于 release 级配置):
helmfile apply --track-mode kubedog --track-timeout 300 --track-logs --track-logs-interval 1s1.2 配置项一览
| 配置项 | 含义 | 默认值 |
|---|---|---|
trackMode | 设置为kubedog启用 kubedog 跟踪;helm-legacy使用 Helm v4 的 legacy 等待模式 | helm |
trackTimeout | 资源跟踪超时时间(秒) | 300 |
trackLogs | 在部署期间打印被跟踪资源的日志 | false |
trackLogsInterval | 日志输出更新的间隔,形如1s、30s | 10s(最小1s) |
trackLogsUntilReady | 在trackLogs: true时,每个 Pod 首次就绪后停止打印常规 Pod 日志 | false |
trackFailedLogs | 仅打印部署期间失败的 Pod 的已收集日志 | false |
只查看失败 Pod 日志时,可在 release 上设置trackFailedLogs: true,或对helmfile apply/helmfile sync使用--track-failed-logs。若两个日志选项同时启用,则打印所有被跟踪 Pod 的日志。
启用 kubedog 跟踪且开启trackLogs或trackFailedLogs后,helmfile apply与helmfile sync默认每 10 秒打印一次收集到的日志。可通过 release 上的trackLogsInterval或命令行--track-logs-interval(如上面的1s)调整间隔。显式提供的命令行 flag 覆盖 release 设置;否则 release 设置优先于10s默认值;最小值是1s。部署进度的变化检查同样每 10 秒进行一次。
从源码看,10s默认值定义在 pkg/kubedog/options.go(defaultLogsInterval = 10 * time.Second),TrackOptions通过WithLogsInterval、WithLogsUntilReady、WithFailedLogsOnly等链式方法装配,见 pkg/kubedog/options.go。
1.3 仅跟踪启动日志(Startup-Only Pod Logs)
设置trackLogsUntilReady: true可以在其他副本仍在启动时,只展示启动日志而不再持续打印已就绪 Pod 的应用流量:
releases: - name: myapp chart: ./charts/myapp trackMode: kubedog trackTimeout: 600 trackLogs: true trackLogsUntilReady: true或使用命令行 flag:
helmfile apply --track-mode kubedog --track-timeout 600 --track-logs --track-logs-until-ready就绪前捕获的日志会被刷新输出;如果同一 Pod 之后变为未就绪或失败,日志输出仍只限于启动阶段,而就绪与失败跟踪对每个 Pod 持续进行;Job 日志保持原有行为。
Kubernetes 的就绪时间戳精度为秒级,因此就绪那一秒的日志会被保留,以免丢失启动输出。该选项默认false,所以trackLogs: true会贯穿整个跟踪过程持续打印日志;它仅在trackLogs启用时生效,单独设置trackFailedLogs: true仍保持原有的"仅失败"行为;当trackLogs与trackFailedLogs同时启用时,trackLogs优先。
该机制的底层实现位于 pkg/kubedog/logs.go:podLogFilter独立于 kubedog 的工作负载就绪判断,只负责过滤输出(Pod 跟踪与日志捕获照常进行)。需要特别注意的是,就绪截止过滤只适用于deploy、sts、ds三类工作负载,Job 被显式排除(pkg/kubedog/logs.go),因为 Job 可能处于 Ready 状态却仍在执行。
1.4 三种跟踪模式(Track Modes)
Helmfile 支持三种trackMode:
helm(默认):使用 Helm 内置的--wait标志进行资源跟踪;helm-legacy:使用 Helm v4 的--wait=legacy标志。适合从 Helm v3 迁移到 Helm v4 的场景——当 Chart 与新 watcher 等待机制存在兼容问题时(例如只有livenessProbe而没有startupProbe的 Chart),可以退回 v3 风格的轮询行为。注意:该模式仅对 Helm v4 生效,配合 Helm v3 时会回退为普通--wait;kubedog:使用 kubedog 进行带详细反馈的高级资源跟踪。
模式解析的优先级从源码可见一斑:pkg/state/helmx.go 的getTrackMode依次取release.TrackMode→SyncOpts.TrackMode→HelmDefaults.TrackMode→ 兜底helm。而 pkg/state/helmx.go 的appendWaitFlags明确:仅当 Helm 为 v4 时才追加--wait=legacy,否则打印警告并追加普通--wait。这一分支逻辑在 pkg/state/helmx_test.go 中有完整的表格化测试覆盖(含 Helm v4 +helm-legacy、Helm v3 回退告警、kubedog模式追加普通--wait等用例)。
1.5 资源过滤(Resource Filtering)
通过白名单/黑名单控制需要跟踪的资源:
releases: - name: myapp chart: ./charts/myapp trackMode: kubedog # 只跟踪特定资源类型 trackKinds: - Deployment - StatefulSet # 跳过某些资源类型 skipKinds: - ConfigMap - Secret1.6 指定资源跟踪(Specific Resource Tracking)
按名称与命名空间只跟踪特定资源:
releases: - name: myapp chart: ./charts/myapp trackMode: kubedog trackResources: - kind: Deployment name: myapp-deployment namespace: default - kind: Job name: myapp-jobtrackResources的每个条目对应源码中的TrackResourceSpec结构(Kind、Name、Namespace三个字段,见 pkg/state/state.go),并在 pkg/state/helmx.go 的convertTrackResources中转换为 kubedog 的resource.Resource列表;随后与trackKinds、skipKinds一起装配进resource.FilterConfig(pkg/state/helmx.go)。
1.7 过滤优先级规则
资源过滤按以下优先级生效(从高到低):
trackResources:白名单指定资源(最高优先级);skipKinds:黑名单资源类型;trackKinds:白名单资源类型。
实际跟踪时,被过滤后保留的资源数量会通过kubedog filter kept N of M resources之类的日志输出(见 pkg/kubedog/tracker.go),便于确认过滤是否符合预期。
1.8 价值与收益
- 实时反馈:以详细状态更新展示部署进度;
- 日志流式输出:部署期间直接查看容器日志;
- 细粒度控制:只跟踪关心的资源;
- 更易排障:部署问题即刻可见。
1.9 Helm v4 Legacy 等待模式
使用 Helm v4 时,若 Chart 存在缺少startupProbe的损坏livenessProbe配置,默认的--wait=watcher模式可能失败。Helm v4 引入了--wait=legacy,采用与 Helm v3 行为兼容的更简单轮询机制。设置trackMode: helm-legacy即可:
releases: - name: myapp chart: ./charts/myapp trackMode: helm-legacy或命令行:
helmfile apply --track-mode helm-legacy1.10 兼容性说明
helm:默认模式,使用 Helm 内置--wait标志;helm-legacy:使用 Helm v4 的--wait=legacy标志(仅 Helm v4 可用);kubedog:使用 kubedog 库进行高级资源跟踪;- Kubedog 跟踪与 Helm 3.x 和 4.x 兼容;
- Kubedog 是编译期依赖,仅在设置
trackMode: kubedog时才被使用; - 适用于部署以下受支持的工作负载类型(当前为
Deployment、StatefulSet、DaemonSet、Job与Canary);其他资源类型仍由 Helm/Helmfile 正常创建,但会被 kubedog 跟踪器忽略。
三种模式常量定义于 pkg/kubedog/options.go:TrackModeHelm = "helm"、TrackModeHelmLegacy = "helm-legacy"、TrackModeKubedog = "kubedog"。
1.11 高级 Kubedog 设置
releases: - name: myapp chart: ./charts/myapp trackMode: kubedog trackTimeout: 600 trackLogs: true kubedogQPS: 5.0 kubedogBurst: 10kubedogQPS:kubedog Kubernetes 客户端的 QPS(每秒查询数),未设置时沿用底层默认值。从源码看,TrackOptions构造时初始化为 QPS100、Burst200(pkg/kubedog/options.go),并可通过WithQPS/WithBurst覆盖;kubedogBurst:kubedog Kubernetes 客户端的 Burst(突发量),未设置时沿用默认值。
补充:
ReleaseSpec还包含trackFailOnError(跟踪失败时是否导致非零退出码)与helmStuckGrace(kubedog 跟踪时针对 Helm v4 钩子等待卡死的"安全阀",详见 pkg/state/state.go),源码中也有对应注释与实现,可作为排障时的进阶选项。
二、向 Helmfile 导入配置参数(vals 集成)
Helmfile 集成了 vals 来从以下后端导入配置参数:
- AWS SSM Parameter Store
- AWS SecretsManager
- Vault
- SOPS
完整后端列表可查阅 vals 项目的 "Supported Backends" 文档。该特性最初实现于 roboll/helmfile 的 PR #906;对设计思路与内部工作机制感兴趣的读者可以审阅该 PR(仓库侧的实现位于 pkg/plugins/vals.go,并配有 pkg/plugins/vals_test.go 测试)。典型用法是在values或environment.values中通过ref+前缀引用后端路径,例如ref+awsssm://...、ref+vault://...、ref+sops://...,Helmfile 会在渲染阶段解析为真实值。实际可用的引用前缀以 vals 支持的语法为准。
三、使用 Helmfile 部署 Kustomization
Helmfile 可以直接部署 kustomize 的 "kustomization"。
大多数 Kustomize 操作通常通过kustomize edit完成,而这些操作都可以声明式地在 Helm 的values.yaml文件中表达。底层实现上,Helmfile 将 kustomization转换成本地临时目录中的 Chart,从而可以通过helm upgrade --install安装。转换分两步完成:先生成临时 kustomization(综合各种选项),再从临时 kustomization 生成临时 Chart。
转换逻辑的伪代码如下:
$ TMPCHART=/tmp/sometmpdir $ mkdir -p ${TMPCHART}/templates $ somehow_generate_chart_yaml ${TMPCHART}/Chart.yaml $ TMPKUSTOMIZATION=/tmp/sometmpdir2 $ somehow_generate_temp_kustomization_yaml ${TMPKUSTOMIZATION}/kustomization.yaml $ kustomize build ${TMPKUSTOMIZATION}/kustomization.yaml > ${TMPCHART}/templates/all.yaml假设你的helmfile.yaml如下:
releases: - name: myapp chart: mykustomization values: - values.yamlHelmfile 首先生成一个临时kustomization.yaml:
bases: - ${ABS_PATH_TO_HELMFILE_YAML}/mykustomization随后依次执行以下步骤:
- 对
values.yaml中生成的每个$IMAGE运行kustomize edit set image $IMAGE; - 按
values.yaml中指定的namePrefix运行kustomize edit set nameprefix $NAMEPREFIX; - 按
values.yaml中指定的nameSuffix运行kustomize edit set namesuffix $NAMESUFFIX; - 按
values.yaml中指定的namespace运行kustomize edit set namespace $NS。
用于 kustomization 的values.yaml示例如下:
images: # kustomize edit set image mysql=eu.gcr.io/my-project/mysql@canary - name: mysql newName: eu.gcr.io/my-project/mysql newTag: canary # kustomize edit set image myapp=my-registry/my-app@sha256:24a0c4b4a4c0eb97a1aabb8e29f18e917d05abfe1b7a7c07857230879ce7d3d3 - name: myapp digest: sha256:24a0c4b4a4c0eb97a1aabb8e29f18e917d05abfe1b7a7c07857230879ce7d3d3 newName: my-registry/my-app # kustomize edit set nameprefix foo- namePrefix: foo- # kustomize edit set namesuffix -bar nameSuffix: -bar # kustomize edit set namespace myapp namespace: myapp至此,Helmfile 可以从你在releases[].chart中指定的基础 kustomization 与values.yaml生成完整的 kustomization,并将其纳入临时 Chart。
最后,Helmfile 像安装普通 Chart 一样安装这个临时 Chart——无论每个应用是以 Helm Chart 还是 kustomization 声明,你都可以用 Helmfile 统一管理。
从源码看,这一"Chart 化"能力由 github.com/helmfile/chartify 与 pkg/state/helmx.go),test/advanced/目录下提供了可直接运行的多套集成用例:test/advanced/helmfile.yaml 及其配套的 kustomapp / kustomapp2(含kustomization.yaml与all.yaml)。
四、对 Helm Chart 进行 Adhoc Kustomize 改造
借助与 Kustomize 的集成,Helmfile 不仅能将 Kustomization 部署为 Helm Chart,还能在安装前对 Chart 做 Kustomize 改造。
提示:以下字段也可以用与
values字段相同的方式指定文件路径。
目前 Helmfile 允许设置以下字段对 Chart 进行 kustomize:
releases[].strategicMergePatchesreleases[].jsonPatchesreleases[].transformers
这些字段在 pkg/state/state.go 中对应JSONPatches、StrategicMergePatches与Transformers(均为[]any,既可以是内联 YAML 映射,也可以是文件路径)。底层处理位于 pkg/state/helmx.go:非内联的补丁条目会被渲染为临时 values 文件(支持模板),再交给 chartify 生成临时 Chart 后统一安装。
4.1strategicMergePatches
通过releases[].strategicMergePatches可以添加/更新 Helm Chart 渲染出的任意 Kubernetes 资源字段:
repositories: - name: incubator url: https://charts.helm.sh/incubator releases: - name: raw1 chart: incubator/raw values: - resources: - apiVersion: v1 kind: ConfigMap metadata: name: raw1 namespace: default data: foo: FOO strategicMergePatches: - apiVersion: v1 kind: ConfigMap metadata: name: raw1 namespace: default data: bar: BAR对上述示例执行helmfile template,会得到一个名为raw1的 ConfigMap,其data为:
foo: FOO bar: BAR注意第二个data字段bar正是来自上面helmfile.yaml中定义的 strategic-merge 补丁。
另外还有releases[].jsonPatches,与strategicMergePatches工作方式类似,但额外支持删除字段。同样可参考 test/advanced/helmfile.yaml 中的补丁示例。
4.2transformers
设置transformers可以应用 Kustomize 的 transformers(关于内置插件的配置方式,可参考 kustomize 官方 "configuring the builtin plugins" 文档)。每个条目可以是 YAML 或 Go 模板文件的路径,也可以是内联的 transformer 声明(YAML 哈希)。
它常用于为资源批量添加公共标签与注解。下面的示例为aws-load-balancer-controllerChart 渲染出的每个资源添加公共注解与标签:
releases: - name: "aws-load-balancer-controller" namespace: "kube-system" forceNamespace: "kube-system" chart: "center/aws/aws-load-balancer-controller" transformers: - apiVersion: builtin kind: AnnotationsTransformer metadata: name: notImportantHere annotations: area: 51 greeting: take me to your leader fieldSpecs: - path: metadata/annotations create: true - apiVersion: builtin kind: LabelTransformer metadata: name: notImportantHere labels: foo: bar fieldSpecs: - path: metadata/labels create: true如前所述,transformers既可以是一组内嵌 transformer,也可以是 YAML 或 Go 模板文件,或三者混用:
transformers: # 内嵌 transformer - apiVersion: builtin kind: AnnotationsTransformer metadata: name: notImportantHere annotations: area: 51 greeting: take me to your leader fieldSpecs: - path: metadata/annotations create: true # YAML 文件 - path/to/transformer.yaml # Go 模板 # 与 release values 文件模板相同的模板参数集可用 - path/to/transformer.yaml.gotmpl关于如何声明 transformers 的更多信息,可参考 kustomize 官方 "configuring the builtin plugins" 文档。
五、不 fork Chart 添加依赖
借助 Helmfile,你可以不 fork 一个 Helm Chart 就为它添加 Chart 依赖。
下面是一个为 releasefoo添加stable/envoy依赖的helmfile.yaml示例:
repositories: - name: stable url: https://charts.helm.sh/stable releases: - name: foo chart: ./path/to/foo dependencies: - chart: stable/envoy version: 1.5当 Helmfile 遇到releases[].dependencies时,它会从./path/to/foo创建另一个临时 Chart,并在其Chart.yaml中添加如下dependencies,从而免去 fork:
dependencies: - name: envoy repo: https://charts.helm.sh/stable condition: envoy.enabled一个 Helm Chart 可以对同一个 Chart 声明两个或更多带不同alias的依赖。像标准Chart.yaml中那样为依赖指定alias即可:
repositories: - name: stable url: https://charts.helm.sh/stable releases: - name: foo chart: ./path/to/foo dependencies: - chart: stable/envoy version: 1.5 alias: bar - chart: stable/envoy version: 1.5 alias: baz这会令临时 Chart 的Chart.yaml变成:
dependencies: - alias: bar name: envoy repo: https://charts.helm.sh/stable condition: bar.enabled - alias: baz name: envoy repo: https://charts.helm.sh/stable condition: baz.enabled该特性有更多背景可参考 issue #649。
在支持对本地 Chart 添加 Adhoc 依赖(#1765)之后,你甚至可以在chart中写相对helmfile.yaml的本地文件路径:
releases: - name: foo chart: ./path/to/foo dependencies: - chart: ./path/to/bar内部实现上,Helmfile 会从本地 Chart./path/to/foo创建另一个临时 Chart,并将 Chart 的Chart.yamldependencies 修改为:
dependencies: - alias: bar name: bar repo: file:///abs/path/to/bar condition: bar.enabled更多细节可参考 issue #1762 的讨论。源码层面,依赖别名默认按namespace-releaseName生成(chartDependenciesAlias,见 pkg/state/chart_dependency.go),并且相对file://依赖会被重写为绝对路径(rewriteChartDependencies,见 pkg/state/state.go)。
5.1 OCI Chart 依赖
从 Helmfile v0.146.0 起,可以将 OCI Chart 加入 Chart 依赖。下面的helmfile.yaml为 releasefoo添加了一个 OCI Chart 依赖:
releases: - name: foo chart: ./path/to/foo dependencies: - chart: oci://my-oci-registry/helm-repo/envoy version: 1.5仓库中相关实现与解析逻辑可参见 pkg/state/chart_dependency.go(OCI Chart 依赖名取路径最后一段、仓库 URL 构造等),并由 pkg/state/oci_chart_lock_test.go、pkg/state/oci_chart_version_test.go、pkg/state/oci_parse_test.go 与 pkg/state/chart_dependencies_rewrite_test.go 等测试覆盖。
六、按环境拆分 Lockfile
某些场景下,CI/CD 流水线希望在使用同一组 Chart 的同时对不同环境(如 staging 与 production)渐进式发布更新。这可以通过将lockFilePath与环境结合实现:
environments: staging: production --- lockFilePath: .helmfile.{{ .Environment.Name}}.lock releases: - name: myapp chart: charts/myapp上面示例中,lockFilePath使用了 Go 模板语法{{ .Environment.Name }},因此 staging 环境会使用.helmfile.staging.lock,production 环境则使用.helmfile.production.lock,互不干扰。lockFilePath字段在源码中对应HelmState.LockFile(yaml:"lockFilePath,omitempty",见 pkg/state/state.go),模板渲染由状态加载流程统一完成。
结语
本文覆盖的六类高级特性让 Helmfile 从"声明式发布 Chart"的工具进一步演化为"统一声明式发布平台":Kubedog 跟踪提供了超越--wait的部署可见性(日志流、资源过滤、三种跟踪模式与 v4 legacy 兼容);vals 集成打通了外部密钥/配置后端;Kustomize 支持让 kustomization 与 Chart 在同一体系中部署,并能对 Chart 做安装前的 Adhoc 改造;依赖注入免去 fork Chart 的维护负担(含本地与 OCI 依赖);按环境拆分 Lockfile 则为渐进式发布提供了基础设施。相关源码与集成用例可继续在 pkg/kubedog、pkg/state/helmx.go、pkg/state/chart_dependency.go 与 test/advanced/helmfile.yaml 中深入研读。
- 云原生
- 运维
- 工具
【免费下载链接】helmfile
Declaratively deploy your Kubernetes manifests, Kustomize configs, and Charts as Helm releases. Generate all-in-one manifests for use with ArgoCD.
相关推荐
Helmfile高级特性解析:Kustomize集成与图表定制
Helmfile高级特性解析:Kustomize集成与图表定制 Helmfile作为强大的Kubernetes应用部署工具,提供了许多高级特性来简化复杂的部署场
Essentia.js项目架构解析:从C++到WebAssembly的音频处理转换指南
Essentia.js项目架构解析:从C++到WebAssembly的音频处理转换指南 🎵 音乐和音频分析 在现代Web应用中变得越来越重要,而Essenti
音频处理机器学习Cordova PushPlugin API详解:从注册到接收通知的完整流程
Cordova PushPlugin API详解:从注册到接收通知的完整流程 Cordova PushPlugin是一款强大的跨平台推送通知插件,支持Andro
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考