chore(helm): template Chart.yaml from Chart.yaml.tmpl - #2307
Conversation
Source-tree Chart.yaml had stale hardcoded versions (helix-runner 0.3.9, helix-sandbox 0.2.2, controlplane recently bumped to 2.9.0) that drift from real releases between manual bumps. Anyone browsing the repo on GitHub or installing from a clone saw the stale numbers. Move the source-of-truth to Chart.yaml.tmpl with a __VERSION__ placeholder and render at build time via scripts/render-charts.sh. The rendered Chart.yaml is gitignored. Tag builds stamp the real release; non-tag builds (lint, dev) get a sentinel "0.0.0-source-not-installable" that makes accidental local installs obviously broken. Also anchored unrelated build-binary entries (helix-runner, zed-build, helix, tmp) in .gitignore to repo root — the unanchored helix-runner pattern was hiding charts/helix-runner/ contents from git. The previously-published 0.x chart packages were already pruned from gs://charts.helixml.tech and index.yaml regenerated. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
chocobar
left a comment
There was a problem hiding this comment.
Self-review. Substantive issues, in order of severity.
Bugs / regressions
1. .gitignore anchoring is over-scoped — regression risk for build artifacts
The PR anchors all four patterns (/helix-runner, /zed-build, /helix, /tmp) when only /helix-runner was actually needed to unshadow charts/helix-runner/. Concrete impact:
api/cmd/helix/is a real source dir. Runninggo buildthere produces anapi/cmd/helix/helixbinary. The old unanchoredhelixrule ignored it; the new/helixrule does not — it'll now show up ingit statusand can be accidentally committed.runner-cmd/helix-runner/is similarly a source dir that producesrunner-cmd/helix-runner/helix-runneron build.
Fix: revert anchoring on helix, zed-build, tmp. Only anchor /helix-runner (the one this PR actually needs). Leaves the broader cleanup for a separate, scoped PR with verified test against a built tree.
2. helm-lint never runs against a real version
.drone.yml helm-lint step has when: event: [push] — it doesn't run on tag events. So the only render that ever gets helm lint-ed is the sentinel 0.0.0-source-not-installable. A Chart.yaml.tmpl that breaks only with real-version substitution (e.g. unquoted __VERSION__ in a place where 2.10.0-rc1 parses differently from 0.0.0-source-not-installable) won't be caught until gen_packages.sh helm package fails mid-release.
Fix: add a lint step that runs DRONE_TAG=v9.9.9-rendertest sh scripts/render-charts.sh && helm lint charts/... so we exercise the real-version path on every push.
3. Inconsistent invocation: sh vs bash
.drone.ymlandscripts/gen_packages.shinvokesh scripts/render-charts.shscripts/repo_sync.shinvokesbash scripts/render-charts.sh
Script shebang is #!/bin/sh. Both work, but pick one. Prefer sh (matches shebang and works in the alpine helm image which only has busybox ash).
Doc gaps
4. Local dev workflow undocumented
A contributor cloning the repo and running helm lint charts/helix-controlplane now gets a Chart.yaml file is missing error. The READMEs say "don't install from source" but don't say "to develop on the chart, run bash scripts/render-charts.sh first." CONTRIBUTING.md isn't updated either.
Fix: one-line note in each chart README under a ## Developing on the chart heading: bash scripts/render-charts.sh then helm lint .. Or add a make charts target.
Nits (won't block)
5. Validation regex isn't anchored at the end
grep -qE '^[0-9]+\.[0-9]+\.[0-9]+' matches any string starting with X.Y.Z, including the sentinel. So the validation only catches truly malformed values like not-a-version. Effectively a no-op for the sentinel path. Acceptable — the validation is a guard against shell errors, not user input.
6. PR description claims "anchored unrelated build-binary entries... so they don't shadow same-named subdirectories"
Connected to #1 — the framing oversells the change as a correctness fix. It's actually a behavioral change that may regress build-artifact ignoring elsewhere.
- .gitignore: scope-back the anchoring to /helix-runner only. Anchoring helix, zed-build and tmp would unmask build artifacts in subdirs (e.g. api/cmd/helix/helix, runner-cmd/helix-runner/helix-runner). - .drone.yml helm-lint: add a re-render+re-lint pass with a synthetic real-looking tag so template breakage that only manifests with a non-sentinel version is caught in PR rather than mid-release. - repo_sync.sh: invoke render-charts.sh via sh to match the script's shebang and the convention used elsewhere. - render-charts.sh: anchor the semver validation regex so it actually rejects suffix garbage (still accepts pre-release / build metadata). - chart READMEs: add a "Developing on the chart" section documenting the render step that's now a prerequisite for helm lint/template. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Summary
version/appVersionsource-of-truth fromChart.yamltoChart.yaml.tmplwith a__VERSION__placeholder. RenderedChart.yamlis now gitignored.scripts/render-charts.shstamps the version from${DRONE_TAG}/${TAG_NAME}(leadingvstripped). Without a tag, it stamps a sentinel0.0.0-source-not-installableso accidental local installs are obviously broken.scripts/gen_packages.shandscripts/repo_sync.shnow delegate torender-charts.shinstead of duplicating the sed..drone.ymlhelm-lintstep renders before anyhelmcommand, then re-renders with a synthetic real-looking tag and re-lints to catch template breakage that only surfaces with a non-sentinel version.render-charts.shstep for chart development..gitignore: anchored only thehelix-runnerpattern (/helix-runner) to unshadowcharts/helix-runner/. Other unanchored patterns (helix,zed-build,tmp) intentionally left as-is to keep ignoring build artifacts in subdirectories likeapi/cmd/helix/helixandrunner-cmd/helix-runner/helix-runner.Why
charts/*/Chart.yamlhad hardcoded versions that went stale between releases (helix-runner0.3.9, helix-sandbox0.2.2, helix-controlplane recently bumped to2.9.0while latest release is 2.10.x). Users browsing the repo on GitHub or runninghelm install ./charts/...from a clone saw stale numbers and got confused about which version was current.Templating eliminates the drift entirely — there's nothing in git that can go stale, and CI always stamps the canonical version at release time.
The previously-published
0.xchart tarballs (61 files: helix-controlplane0.1.x-0.3.x, helix-runner0.1-0.3, helix-sandbox0.1-0.2) have already been removed fromgs://charts.helixml.techandindex.yamlregenerated. The repo at https://charts.helixml.tech now only lists2.xversions.Test plan
bash scripts/render-charts.shwith no tag produces sentinel and prints WARN lines on stderrDRONE_TAG=v2.10.0 sh scripts/render-charts.shproducesversion: 2.10.0/appVersion: "2.10.0"(leadingvstripped)DRONE_TAG=v2.10.0-rc1 sh scripts/render-charts.shaccepts pre-release suffixDRONE_TAG=v2.10.0+build.5 sh scripts/render-charts.shaccepts build metadataDRONE_TAG=not-a-version sh scripts/render-charts.shfails fast with semver validation errorhelm dependency build,helm lint,helm templateall pass on rendered output for all 3 charts (sentinel and synthetic-tag variants)helm packageof rendered charts produces correctly-named tarballs (helix-runner-2.10.0.tgzetc.)Chart.yamlcorrectly excluded from git via.gitignore(git check-ignoreconfirms)Chart.yaml.tmplfor all 3 charts visible to git (no longer shadowed by thehelix-runnerrule)helm-lintstep passes on this PR — including the new synthetic-tag re-lint passtgzhas the right version stamped (do on first real release after merge)🤖 Generated with Claude Code