feat: Add ConditionTemplate support in releaseSpec#2669
Conversation
Signed-off-by: Arthur Garreau <arthur.garreau98@gmail.com>
|
I created this PR in order to resolve #2665. I'm not proficient in Go so any advice is welcome. The main problem was that we currently accept a path and not directly a boolean, so I made this little hack to cast the template result into a string and cast it back as a boolean. This keeps backward compatibility but for sure is not the cleanest. |
Code Review: ConditionTemplate supportOverall this is a clean, well-scoped PR that follows the existing 🔴 Bugs / should fix1. Wrong field name in error message ( The new return nil, fmt.Errorf("failed executing template expressions in release \"%s\".version = \"%s\": %v", r.Name, ts, err)This is a copy-paste from the pre-existing buggy "...in release \"%s\".conditionTemplate = \"%s\": %v"(FWIW, the same typo in the three older blocks is worth a follow-up cleanup.) 🟡 Correctness / design concerns2. Silent discard of In 3. Behavior change in Previously 4. go-yaml treats 🟢 Test gaps5. Dead A
So the field is vestigial and suggests a misunderstanding of the flow. Either remove it, or — better — add tests in 6. Missing coverage
🔵 Nit7. Doc inconsistency
Summary: The core feature is correctly implemented and follows house patterns. Before merge I'd ask for at least #1 (error message) and #5/#6 (test cleanup + precedence/error coverage). #3 deserves a changelog note. The rest are doc/polish. |
Deep review: data-flow, design, and edge casesDid a deeper pass tracing the actual execution paths. Findings below, most-impactful first. 1.
|
|
Hello @yxxhero, I just updated the PR with the following changes :
On the |
Signed-off-by: Arthur Garreau <arthur.garreau98@gmail.com>
fb8df88 to
6c762d2
Compare
yxxhero
left a comment
There was a problem hiding this comment.
Review: feat: Add ConditionTemplate support in releaseSpec
Overall the feature is well-designed and mirrors the existing installedTemplate/waitTemplate/verifyTemplate lifecycle cleanly. The new unit tests pass and golangci-lint is clean. Requesting changes because the PR breaks the pre-existing TestGenerateID suite (see below).
🔴 Blocker — breaks TestGenerateID (CI-failing)
Adding ConditionTemplate *string to ReleaseSpec changes the struct's spew serialization, which feeds the FNV hash in generateValuesID (pkg/state/temp.go:66). As a result the golden hashes hardcoded in pkg/state/temp_test.go are now stale:
go test ./pkg/state/... -run TestGenerateID # FAILS
I reproduced this deterministically on this PR branch; main passes. The 6 want values in temp_test.go need updating:
| Case | Old | New |
|---|---|---|
| baseline (L41) | foo-values-6fcd6fc479 |
foo-values-6765d87f7c |
| different bytes content (L48) | foo-values-6556658b7b |
foo-values-6d7db5f8b |
| different map content (L55) | foo-values-fd86f44b |
foo-values-5c55f66dd |
| different chart (L61) | foo-values-58bdc49774 |
foo-values-7665888bf4 |
| different name (L67) | bar-values-856b998888 |
bar-values-bc6f974bd |
| specific ns (L73) | myns-foo-values-7bdfd95fbd |
myns-foo-values-76f8c7c596 |
(Yes, this golden-hash approach is fragile to any ReleaseSpec field addition — but the update belongs in this PR so make test stays green.)
🟡 Minor — CHANGELOG placement (CHANGELOG.md:3)
The new ### Added block is inserted under ## [1.4.1] - 2026-03-03, which is already shipped (latest release is v1.6.0). It belongs in a new ## [Unreleased] section at the top.
🟡 Minor — stale doc comment (pkg/state/state.go:3357)
This line is now inaccurate:
// If the condition is specified but not in the form 'foo.enabled', it returns an error.
After this PR, true/false literals are not in foo.enabled form yet they no longer error. Worth reconciling with the newly inserted "cast boolean" line above it.
🟢 Nits
setConditionFromBool(pkg/state/state_exec_tmpl.go:51) is a single-use one-liner (r.Condition = fmt.Sprintf("%t", condition)); could be inlined, though harmless.- Grammar: "casted boolean" → "cast boolean" (
castis already past tense). - Like the other
*Templatefields, when bothconditionandconditionTemplateare set, the originalconditionis silently overwritten with no log. Consistent with existing behavior, but alogger.Debugfwould help users debugging precedence.
✅ What's good
- Design parity with the other templated bool fields: render in
ExecuteTemplateExpressions→ resolve to bool inupdateBoolTemplatedValues→ nil out the template field. Precedence (conditionTemplateoverridescondition) is correctly implemented and tested (state_exec_tmpl_test.go:113). - The
release.goerror-message fixes (".version ="→".waitTemplate ="/".installedTemplate ="/".verifyTemplate =") are a welcome drive-by fix for copy-paste bugs. condition: true/falseliteral handling is backward-compatible — it converts a previous hard error ("must be in the form 'foo.enabled'") into valid behavior.strings.ToLowercorrectly handlesTrue/FALSE.- Test coverage is solid: true/false literals, precedence, unresolvable template (
{{ "maybe" }}), and YAML bool unmarshal. golangci-lint: 0 issues;go vet: clean.
This pull request adds support for a new
conditionTemplatefield for Helmfile releases, allowing users to specify dynamic, templated conditions for enabling or disabling releases. It also improves the handling of theconditionfield to accept boolean literals (true/false) directly, and updates documentation and tests to reflect these enhancements.New Features:
conditionTemplatefield inReleaseSpec, which allows release conditions to be specified as Go templates that must render to a boolean. If set,conditionTemplatetakes precedence overcondition[1] [2] [3] [4].conditionTemplatein the release templating logic, converting the rendered result to a boolean and updating the release'sconditionaccordingly [1] [2].Improvements to Condition Handling:
conditionfield to directly accept boolean literals (true/false) in addition to value lookups, simplifying configuration for static conditions [1] [2] [3].Documentation Updates:
conditionTemplatefield, its precedence, and the expanded capabilities of theconditionfield [1] [2] [3] [4].Testing:
conditionTemplateand the new boolean literal handling forcondition[1] [2] [3] [4].