Skip to content

feat: implement HIP-0025 resource creation sequencing#32314

Open
caretak3r wants to merge 7 commits into
helm:mainfrom
caretak3r:feature/hip-0025-sequencing
Open

feat: implement HIP-0025 resource creation sequencing#32314
caretak3r wants to merge 7 commits into
helm:mainfrom
caretak3r:feature/hip-0025-sequencing

Conversation

@caretak3r

Copy link
Copy Markdown

What this PR does / why we need it

Implements HIP-0025: Better Support for Resource Creation Sequencing, adding native DAG-based ordering for resource groups and subcharts to Helm v4.

Today Helm applies all rendered manifests simultaneously. Application distributors who need ordered deployment must use hooks (tedious to maintain) or bake sequencing into the application itself (unnecessary complexity). HIP-0025 gives chart authors a first-class mechanism to define deployment order using annotations and Chart.yaml fields, and gives operators a --wait=ordered flag to enable sequenced execution.


Overview

When --wait=ordered is specified, Helm builds two levels of dependency graphs:

  1. Subchart DAG — orders subcharts based on depends-on fields in Chart.yaml dependencies and/or the helm.sh/depends-on/subcharts annotation.
  2. Resource-group DAG — within each chart level, orders groups of resources based on helm.sh/resource-group and helm.sh/depends-on/resource-groups annotations.

Resources are deployed in topological order (Kahn's algorithm). Helm waits for each batch to reach readiness before proceeding to the next. Readiness defaults to kstatus evaluation; chart authors can override it with custom JSONPath expressions via helm.sh/readiness-success and helm.sh/readiness-failure annotations supporting 6 operators (==, !=, <, <=, >, >=).

Execution Flow

┌─────────────────────────────────────────┐
│         Subchart DAG Resolution         │
│  (Chart.yaml depends-on / annotations)  │
└──────────────────┬──────────────────────┘
                   │
         ┌─────────▼──────────┐
         │  For each subchart  │◄─── topological batch order
         │  batch — recursive  │     (chartPath threaded through
         │  into nested deps   │      arbitrary nesting depth)
         └─────────┬──────────┘
                   │
    ┌──────────────▼──────────────┐
    │  Resource-Group DAG within  │
    │  each chart (annotations)   │
    └──────────────┬──────────────┘
                   │
         ┌─────────▼──────────┐
         │  Deploy group batch │
         │  Wait for readiness │──── kstatus or custom JSONPath
         │  Next group batch   │
         └────────────────────┘

Reverse-DAG order is used for uninstall and rollback of sequenced releases.


Commit Organization

This PR was previously organized as 7 stacked commits to aid review. Following review iterations and a rebase onto current upstream/main, it has been consolidated into 2 commits to keep the history clean:

# Commit Scope
1 feat: implement HIP-0025 resource creation sequencing The full implementation: generic DAG engine, resource-group + subchart parsers, two-level execution wired into install/upgrade/rollback/uninstall/template, lint rules, custom readiness, and tests.
2 fix(hip-0025): thread context through updateAndWait and chartPath through nested subcharts Addresses two findings from Copilot's most recent review of commit 1 (see Review Feedback below).

New Annotations

Annotation Scope Purpose
helm.sh/resource-group Resource Assigns the resource to a named group
helm.sh/depends-on/resource-groups Resource Declares resource-group ordering dependencies (JSON array)
helm.sh/depends-on/subcharts Chart.yaml Declares parent→subchart ordering dependencies (JSON array)
helm.sh/readiness-success Resource Custom JSONPath success conditions (OR semantics)
helm.sh/readiness-failure Resource Custom JSONPath failure conditions (OR semantics, takes precedence)

All six annotation keys match the HIP-0025 specification byte-for-byte. The helm.sh/depends-on/resource-groups and helm.sh/depends-on/subcharts keys contain multiple / (not valid Kubernetes qualified names) — these are stripped before SSA-applying to the API server, so K8s never sees them; they are consumed at render/sequencing time only.

New Chart.yaml Fields

  • depends-on on dependencies[] entries — declares subchart ordering dependencies by name or alias.

New CLI Flags

Flag Commands Description
--wait=ordered install, upgrade, rollback, uninstall Enables sequenced deployment / reverse-sequenced teardown
--readiness-timeout install, upgrade, rollback Per-batch readiness timeout (default 1m, must not exceed --timeout)

Schema Changes

  • DependsOn []string added to chart.Dependency (preserves backward compatibility — optional field).
  • SequencingInfo struct added to release.Release (Enabled bool, Strategy string). Persisted with the release so rollback/uninstall know to use sequenced flow.
  • OrderedWaitStrategy constant added to pkg/kube.

Key Design Decisions

  • Generic DAG engine. Topological sort decoupled from Helm-specific types, independently testable (pkg/chart/v2/util/dag.go).
  • Two-level execution. Subchart ordering decides when a chart is processed; resource-group ordering decides how resources within that chart are batched.
  • chartPath threading through recursion. Nested subchart manifests are routed correctly at arbitrary depth — parent → parent/charts/sub → parent/charts/sub/charts/nested.
  • Fixed-point cascade pruning. Resource groups whose dependencies reference unknown groups are pruned and emitted to the unsequenced (last) batch with a warning.
  • Backward compatibility. Charts without sequencing annotations behave identically to before. Releases created without --wait=ordered are upgraded/rolled back/uninstalled using the traditional single-batch flow. The SequencingInfo.Enabled flag gates the sequenced path on rollback and uninstall.
  • Hook exclusion. Hook resources are explicitly excluded from sequencing DAGs; they continue to use helm.sh/hook-weight as before.
  • Spec-faithful annotation keys. helm.sh/depends-on/resource-groups is invalid as a K8s annotation key (multiple /); it's stripped from manifests before SSA. helm template --wait=ordered output emits ## START/END delimiters and is not intended to be piped directly to kubectl apply.

Review Feedback Addressed

Joejulian's CHANGES_REQUESTED feedback (April 2026) has been addressed in commit 1:

  • subchart_dag.go — use ProcessDependencies-resolved chart state. BuildSubchartDAG now reads c.Dependencies() (post-processed: aliases applied, disabled deps pruned, conditions/tags resolved) instead of re-deriving enablement from chart.Metadata.Dependencies heuristics. Closes the misclassification path joejulian called out for conditions/tags/aliases.
  • sequencing.go — context cancellation through createAndWait. Added ctx.Done() select gates before Build, before Create, and before Wait. New test TestSequencedDeployment_CreateAndWait_RespectsContextCancellation covers the four cancellation points.

Latest Copilot review on the consolidated commit (May 3 2026) flagged two further issues, addressed in commit 2:

  • updateAndWait ignored its context arg. Sequenced upgrades and rollbacks did not honor cancellation through Build/Update/Wait. Now threaded with the same select gates as createAndWait.
  • GroupManifestsByDirectSubchart flattened nested subcharts. Used the bare chart name as path prefix; on recursion the prefix didn't match top-level-rooted manifest names. Now threads chartPath through deployChartLevel and deleteChartLevelReverse so each recursion level matches the full path. Added TestSequencing_GroupManifestsByDirectSubchart_Nested; updated the uninstall test that previously documented this as "a known limitation."

Deferred (tracked for follow-up issues, not blockers):

  • JSONPath compilation caching (perf-only; Copilot low-confidence).
  • Parallel execution within a subchart batch — current implementation is sequential within each batch; parallel execution is a tracked enhancement (needs error aggregation and log-interleaving handling) and can be added without breaking the interface.
  • Shared groupManifestsByChartPath helper between cmd/template.go and action/sequencing.go (acknowledged scope-deferred).
  • One-shot warning emission for partial readiness annotations (currently logged each poll iteration).
  • Stripping # Source: headers in normalizedManifestContent for uninstall path recovery.

How to Test

Unit tests:

make test-unit

# Sequencing-specific:
go test ./pkg/chart/v2/util/ -run TestDAG -v
go test ./pkg/chart/v2/util/ -run TestSubchart -v
go test ./pkg/release/v1/util/ -run TestResourceGroup -v
go test ./pkg/kube/ -run TestReadiness -v
go test ./pkg/action/ -run TestSequenc -v
go test ./pkg/action/ -run TestUninstall_Sequenced -v
go test ./pkg/chart/v2/lint/rules/ -run TestSequencing -v
go test ./pkg/cmd/ -run 'TestTemplate|TestReadinessTimeout|TestWaitFlag' -v

Integration tests (requires kind cluster):

kind create cluster --name helm-hip-0025

# Sequenced install with resource groups
helm install rg-demo ./testcharts/resource-groups --wait=ordered

# Subchart ordering (nested ≥3 levels exercises the chartPath fix)
helm install sc-demo ./testcharts/subchart-ordering --wait=ordered

# Custom readiness with JSONPath
helm install cr-demo ./testcharts/custom-readiness --wait=ordered --readiness-timeout 30s

# Template output with delimiters
helm template my-release ./testcharts/resource-groups --wait=ordered

# Reverse-sequenced uninstall
helm uninstall sc-demo --wait=ordered

# Lint
helm lint ./testcharts/circular-dep

kind delete cluster --name helm-hip-0025

Manual verification checklist:

  • Plain charts (no sequencing annotations) behave identically to before
  • helm template with --wait=ordered shows resource-group delimiters
  • helm lint errors on circular deps, partial readiness, orphan refs (ErrorSev)
  • Install/upgrade respects topological order of subcharts and resource groups
  • Rollback/uninstall processes groups in reverse order, recursing through nested subcharts
  • --readiness-timeout is honored per resource group; rejected when greater than --timeout
  • Releases store SequencingInfo when --wait=ordered is used; rollback/uninstall consult it

Reference Documents


Special notes for reviewers:

  • 52 files changed, +7110/−158 net. The consolidated history is intentional: linear rebase -i on the previous 19-commit branch produced N rounds of conflicts against current upstream after the Go-1.26 / k8s-1.36 merge; a one-shot 3-way merge --squash from a fresh branch on upstream/main resolved cleanly.
  • All unit tests pass: pkg/action, pkg/cmd, pkg/kube, pkg/chart/..., pkg/release/.... make lint / make vet clean.
  • DCO ✅ on both commits.

If applicable:

  • This PR contains documentation updates needed (companion: helm/helm-www#2068)
  • This PR contains unit tests
  • This PR has been tested for backwards compatibility

Signed-off-by: Rohit Gudi 50377477+caretak3r@users.noreply.github.com
refs https://github.com/helm/community/blob/main/hips/hip-0025.md

caretak3r added 7 commits July 8, 2026 20:23
Generic DAG with deterministic topological batching and cycle detection,
the subchart dependency DAG builder (reading depends-on field and the
helm.sh/depends-on/subcharts annotation against post-processed
c.Dependencies() state), and the new depends-on field on Chart.yaml
dependency entries.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
…adata

Resource-group annotation parsing into a DAG, the SequencingInfo field
recorded on releases for sequenced uninstall/rollback, and the
helm-internal annotation stripping helper. Backward-compatible JSON
round-trip for releases stored without SequencingInfo.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
OrderedWaitStrategy, custom readiness evaluation via .status-scoped
JSONPath expressions (helm.sh/readiness-success / -failure), and the
status reader that layers custom readiness over kstatus.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
Lint validation for subchart and resource-group dependency cycles,
orphan group references, and the both-or-neither readiness annotation
rule.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
The sequenced deployment engine driving per-batch create-and-wait
across the resource-group and subchart DAGs, wired into install,
upgrade, rollback (respecting stored SequencingInfo), and reverse-order
uninstall. Default (non-ordered) paths are unchanged.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
…command

The --wait=ordered and --readiness-timeout flags across
install/upgrade/uninstall/rollback, ordered helm template output with
resource-group delimiters, and the helm dag debugging command.

Refs: HIP-0025
Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
…ion keys

Address Copilot review on PR helm#32038:
- dag.go: printChild returned early for subcharts whose chart metadata is
  unavailable (storage-decoded charts at rollback/uninstall), hiding the
  structural resource-group batches buildStructuralLevel generates. Print
  an accurate note and still recurse into the structural child level. The
  old 'not found in chart dependencies' message was also misleading.
- sequencing.go: hoist HelmInternalSequencingAnnotations() out of the
  per-resource Visit closure so the slice is cloned once per batch.

Signed-off-by: Rohit Gudi <50377477+caretak3r@users.noreply.github.com>
Copilot AI review requested due to automatic review settings July 9, 2026 01:32
@pull-request-size pull-request-size Bot added the size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. label Jul 9, 2026

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Implements HIP-0025 resource creation sequencing for Helm v4 by introducing a pure, DAG-driven sequencing planner (subchart + resource-group DAGs) and wiring it into CLI/template output, lint, and action flows (install/upgrade/rollback/uninstall) with optional per-resource custom readiness.

Changes:

  • Added generic DAG utilities plus sequencing plan builder to compute ordered apply/delete batches across subcharts and resource groups.
  • Integrated --wait=ordered and --readiness-timeout into commands/actions, including reverse-order rollback/uninstall behavior and release schema gating.
  • Added custom JSONPath-based readiness evaluation and comprehensive unit/golden coverage, plus a helm dag diagnostics command and sequencing lint rules.

Reviewed changes

Copilot reviewed 77 out of 77 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
pkg/release/v1/util/resource_group.go Resource-group annotations parsing + DAG builder
pkg/release/v1/util/resource_group_test.go Resource-group parsing/DAG tests
pkg/release/v1/util/manifest.go Strip invalid sequencing annotation keys from template/apply output
pkg/release/v1/util/manifest_test.go Stripping behavior tests
pkg/release/v1/sequence/plan.go Sequencing plan types + reverse/display helpers
pkg/release/v1/sequence/plan_test.go Plan helper tests + import-purity check
pkg/release/v1/sequence/manifest_parse.go Parse stored/template manifests into typed manifests
pkg/release/v1/sequence/builder.go Plan builder: subchart batching + resource-group batching
pkg/release/v1/release.go Release schema: sequenced marker + legacy decoding
pkg/release/v1/release_test.go Release schema compatibility tests
pkg/kube/statuswait.go Custom readiness integration into status waiter
pkg/kube/readiness.go JSONPath readiness expression parsing/validation/eval
pkg/kube/options.go Wait options: enable custom readiness
pkg/kube/custom_readiness_status_reader.go StatusReader wrapper implementing custom readiness
pkg/kube/client.go Ordered wait strategy + status watcher wiring
pkg/kube/client_wait_strategy_test.go Ordered wait/custom readiness option tests
pkg/cmd/upgrade.go Propagate readiness-timeout; enable ordered wait flag
pkg/cmd/uninstall.go Enable ordered wait flag
pkg/cmd/uninstall_test.go CLI test: uninstall --wait=ordered
pkg/cmd/testdata/testcharts/sequenced-isolated-chart/templates/dd-plain.yaml Test chart manifest (unsequenced resource)
pkg/cmd/testdata/testcharts/sequenced-isolated-chart/templates/cc-gamma.yaml Test chart manifest (isolated group)
pkg/cmd/testdata/testcharts/sequenced-isolated-chart/templates/bb-beta.yaml Test chart manifest (depends-on group)
pkg/cmd/testdata/testcharts/sequenced-isolated-chart/templates/aa-alpha.yaml Test chart manifest (root group)
pkg/cmd/testdata/testcharts/sequenced-isolated-chart/Chart.yaml Test chart metadata
pkg/cmd/testdata/testcharts/sequenced-chart/templates/cc-unsequenced-configmap.yaml Test chart manifest (unsequenced)
pkg/cmd/testdata/testcharts/sequenced-chart/templates/bb-app-configmap.yaml Test chart manifest (group + depends-on)
pkg/cmd/testdata/testcharts/sequenced-chart/templates/aa-databases-configmap.yaml Test chart manifest (group)
pkg/cmd/testdata/testcharts/sequenced-chart/charts/worker/templates/aa-worker-configmap.yaml Subchart test manifest (group)
pkg/cmd/testdata/testcharts/sequenced-chart/charts/worker/Chart.yaml Subchart metadata
pkg/cmd/testdata/testcharts/sequenced-chart/Chart.yaml Test chart metadata + dependency
pkg/cmd/testdata/output/template-ordered-isolated.txt Golden: ordered template output (isolated demotion)
pkg/cmd/testdata/output/template-ordered-delimiters.txt Golden: ordered template output (delimiters)
pkg/cmd/testdata/output/dag-sequenced-isolated.txt Golden: helm dag output (isolated)
pkg/cmd/testdata/output/dag-sequenced-chart.txt Golden: helm dag output (sequenced chart)
pkg/cmd/template.go Ordered template rendering + stripping + warnings
pkg/cmd/template_test.go Ordered template tests + compat/strip invariants
pkg/cmd/root.go Register dag command
pkg/cmd/rollback.go Enable ordered wait + readiness-timeout
pkg/cmd/install.go Enable ordered wait + readiness-timeout
pkg/cmd/get_manifest.go Clarify verbatim stored manifest output behavior
pkg/cmd/get_manifest_test.go Test: get manifest prints stored annotations verbatim
pkg/cmd/flags.go --wait=ordered parsing + readiness-timeout flag
pkg/cmd/flags_test.go Flag parsing tests (wait/readiness-timeout)
pkg/cmd/dag.go New helm dag command (diagnostics)
pkg/cmd/dag_test.go helm dag golden + error-path tests
pkg/chart/v2/util/subchart_dag.go Build subchart DAG from depends-on + annotation
pkg/chart/v2/util/dependencies.go Rewrite depends-on refs before alias rewrite
pkg/chart/v2/util/dag.go Generic DAG implementation
pkg/chart/v2/util/dag_test.go Generic DAG tests
pkg/chart/v2/lint/rules/sequencing.go Sequencing lint rule: plan build + readiness validation
pkg/chart/v2/lint/lint.go Register sequencing lint rules
pkg/chart/v2/lint/lint_test.go Lint integration test for sequencing rules
pkg/chart/v2/dependency.go Add depends-on to chart dependencies schema
pkg/chart/v2/dependency_test.go DependsOn sanitization test
pkg/chart/v2/dependency_json_test.go JSON/YAML schema compatibility tests
pkg/action/warning_system_test.go Action-layer warning surface tests
pkg/action/validate.go Fail-fast on nil REST client in conflict checks
pkg/action/validate_test.go Nil-client regression test
pkg/action/sequencing.go Sequenced apply/delete engine + stripping + batch waits
pkg/action/rollback.go Sequenced rollback path + sequencing-gated behavior
pkg/action/rollback_test.go Rollback sequencing-annotation strip regression test
pkg/action/install.go Sequenced install path + plan build preflight
pkg/action/hooks.go Strip sequencing annotations from hook resources
pkg/action/hooks_test.go Hook strip regression test
pkg/action/backward_compat_test.go Backward-compat scenarios for ordered wait + rollback
pkg/action/action.go Render resources returns sorted manifests for sequencing

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +269 to +275
func isExactYAMLKeyLine(line string, indent int, key string) bool {
body := lineBody(line)
if yamlLineIndent(line) != indent {
return false
}
return strings.TrimRight(body[indent:], " \t") == key+":"
}
Comment on lines +310 to +330
switch entry[0] {
case '\'', '"':
quote := entry[0]
end := strings.IndexByte(entry[1:], quote)
if end == -1 {
return "", false
}
key := entry[1 : end+1]
rest := entry[end+2:]
if !strings.HasPrefix(rest, ":") {
return "", false
}
return key, true
default:
for _, key := range helmInternalSequencingAnnotations {
if strings.HasPrefix(entry, key+":") {
return key, true
}
}
return "", false
}
@promptless-for-oss

Copy link
Copy Markdown

Promptless prepared a documentation update related to this change.

Triggered by helm/helm#32314 (HIP-0025 resource creation sequencing).

The docs for HIP-0025 have been updated to match this implementation: documenting --wait=ordered and --readiness-timeout across install/upgrade/rollback/uninstall, the helm.sh/resource-group, helm.sh/depends-on/resource-groups, helm.sh/depends-on/subcharts, and helm.sh/readiness-success/helm.sh/readiness-failure annotations, the depends-on Chart.yaml field, custom JSONPath readiness semantics, helm template --wait=ordered marker behavior, and the new lint rules. Example annotation values were also corrected to valid single-quoted JSON strings.

Review: Document HIP-0025 resource sequencing (docs PR #2068)

@kunalworldwide kunalworldwide left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a large but well-structured implementation of HIP-0025. The two-level DAG approach — subchart dependencies plus resource-group annotations — gives chart authors flexibility without forcing everyone to adopt sequenced installs.

A few things that stand out:

  • The backward-compat tests are important: --wait=ordered is new, but existing --wait behavior must remain unchanged. The test file covers that.
  • The lint rule for sequencing is a good safety net; invalid dependsOn references will be caught at helm lint time rather than at install time.
  • The DAG utility in pkg/chart/v2/util/dag.go is reusable and well-scoped.

One question: the dependsOn field in Chart.yaml uses chart/subchart names. Is there validation to prevent circular subchart dependencies, and if so, where does the cycle error surface? I see DAG construction in subchart_dag.go but didn't spot an explicit cycle check in the diff.

LGTM otherwise.

@caretak3r

Copy link
Copy Markdown
Author

@kunalworldwide

A couple things to note:

  1. subchart DAGs and resource group DAGs share one implementation, and BuildSubchartDAG only constructs the graph

  2. the check is in DAG.GetBatches()

    // GetBatches performs a topological sort using Kahn's algorithm and returns
    // the nodes grouped into deployment batches. Each batch contains nodes that
    // can be deployed in parallel. Batches are ordered: batch 0 has no prerequisites,
    // batch 1 depends only on batch 0, etc.
    //
    // Returns an error if a cycle is detected, including the names of the nodes
    // involved in the cycle.
    func (d *DAG) GetBatches() ([][]string, error) {
    if len(d.nodes) == 0 {
    return nil, nil
    }
    inDegree := make(map[string]int, len(d.inDegree))
    maps.Copy(inDegree, d.inDegree)
    var batches [][]string
    processed := 0
    for {
    var batch []string
    for node := range d.nodes {
    if inDegree[node] == 0 {
    batch = append(batch, node)
    inDegree[node] = -1
    }
    }
    if len(batch) == 0 {
    break
    }
    sort.Strings(batch)
    batches = append(batches, batch)
    processed += len(batch)
    for _, node := range batch {
    for _, dependent := range d.edges[node] {
    inDegree[dependent]--
    }
    }
    }
    if processed == len(d.nodes) {
    return batches, nil
    }
    cycleNodes := make([]string, 0, len(d.nodes)-processed)
    for node := range d.nodes {
    if inDegree[node] > 0 {
    cycleNodes = append(cycleNodes, node)
    }
    }
    sort.Strings(cycleNodes)
    return nil, fmt.Errorf("cycle detected among nodes: %s", strings.Join(cycleNodes, ", "))
    }

  3. the loop is rejected earlier

    // AddEdge adds a directed edge: "to" depends on "from" (from is deployed before to).
    // Returns an error if either node is unknown or if a self-loop is requested.
    func (d *DAG) AddEdge(from, to string) error {
    if from == to {
    return fmt.Errorf("self-loop not allowed: %q", from)
    }
    if _, ok := d.nodes[from]; !ok {
    return fmt.Errorf("unknown node %q", from)
    }
    if _, ok := d.nodes[to]; !ok {
    return fmt.Errorf("unknown node %q", to)
    }
    key := from + "\x00" + to
    if _, exists := d.edgeSet[key]; exists {
    return nil
    }
    d.edgeSet[key] = struct{}{}
    d.edges[from] = append(d.edges[from], to)
    d.inDegree[to]++
    return nil
    }

  4. the builder calls GetBatches() and wraps the error with domain/chart path to subchart and resource-group cycles are distinguishable

batches, err := dag.GetBatches()
if err != nil {
return fmt.Errorf("subchart circular dependency detected in %s: %w", chartPath, err)
}

groupBatches, err := dag.GetBatches()
if err != nil {
return fmt.Errorf("resource-group circular dependency detected in %s: %w", chartPath, err)
}

since the plan is built up-front this should fail fast before any resource is applied (helm install or helm upgrade or helm template —wait=ordered). the check being in dag.go versus subchart_dag.go is easy to miss - I will add a doc to BuildSubchartDAG pointing to GetBatches to make this easier for new reviewers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants