advanced~4h

Packaging: Helm 3 & Kustomize

Two complementary tools manage manifest complexity. Helm 3 uses templating plus chart packaging plus release lifecycle management. Kustomize uses structured overlay files that transform base manifests

Two complementary tools manage manifest complexity. Helm 3 uses templating plus chart packaging plus release lifecycle management. Kustomize uses structured overlay files that transform base manifests for different environments with no templates and no render step.

  • Helm 3 renders Go templates from a chart's templates/ directory combined with values into raw Kubernetes manifests.

  • Release state stored as a Secret in the target namespace. No Tiller in Helm 3 -- operations use invoking user's kubeconfig.

  • Kustomize is a pure patch/overlay system: a base directory with plain YAML, overlays add/modify via strategic merge patches.

  • Both can be combined: helm template renders to manifests that become a Kustomize base.

  • For Helm: scaffold a chart (helm create ) with Chart.yaml, values.yaml, and a templates/ directory of Go-templated manifest files.

  • Parameterize the manifests in templates/ with {{ .Values.* }} references, and define sane defaults in values.yaml.

  • Install a release with helm install -f values-prod.yaml, layering environment-specific value overrides on top of the chart defaults.

  • Upgrade with helm upgrade, and roll back with helm rollback using Helm's tracked release history (stored as a Secret in the target namespace).

  • For Kustomize: start with a base/ directory of plain, un-templated Kubernetes YAML plus a kustomization.yaml listing those resources.

  • Create overlays/ (e.g. overlays/staging, overlays/production) each with their own kustomization.yaml applying strategic-merge or JSON patches on top of the shared base, then apply with kubectl apply -k overlays/production.

  • Publishing a reusable Helm chart for an internal platform service so every team installing it gets consistent defaults, customized per-team only via values.yaml overrides.

  • Using Kustomize overlays for dev/staging/production variants of the same base manifests -- same Deployment, different replica counts and resource limits per overlay, with no templating logic to maintain.

  • Combining both: helm template renders a third-party chart (e.g. a database operator) down to plain manifests, which then become a Kustomize base for further environment-specific patching.

  • Using helm rollback to revert a bad production release to the previous known-good revision during an incident, using Helm's built-in release history instead of manual git-revert-and-reapply.

  • A platform team maintaining a library of Kustomize bases for common patterns (e.g. a standard Deployment+Service+HPA trio) that individual services overlay with their own image and config.

  • Keep Helm chart values.yaml well-documented with comments and sensible defaults -- a chart with cryptic, undocumented values is hard for other teams to safely adopt.

  • Use helm template locally (or in CI) to review the exact rendered manifests before install/upgrade, since Go template logic can produce subtly wrong YAML that's hard to spot from the template source alone.

  • Prefer Kustomize's strategic-merge patches over full-resource replacement in overlays -- smaller, targeted patches are easier to review and less likely to silently drop fields the base defines.

  • Pin chart versions explicitly in CI/CD (not just 'latest') so deployments are reproducible.

  • Structure Kustomize overlays to differ minimally from the base -- if an overlay patches nearly every field, that's usually a sign the base isn't shared enough to be worth the indirection.

  • Use helm diff (plugin) or kustomize build | kubectl diff -f - before applying changes in production, to see exactly what will change before it does.

  • Writing complex conditional logic deep inside Helm Go templates instead of keeping charts simple -- hard-to-read templates become hard-to-debug production incidents when a value doesn't render as expected.

  • Assuming helm upgrade is always safe -- a chart change combined with a values change can trigger far more resource replacement than expected; always review with helm diff or --dry-run first.

  • Duplicating near-identical full manifests across Kustomize overlays instead of patching a shared base -- defeats the purpose of Kustomize and multiplies drift risk.

  • Forgetting Helm 3 stores release state as a Secret in the target namespace -- deleting that namespace loses Helm's own history/rollback capability even if the actual resources are managed elsewhere.

  • Not pinning chart versions in production deployment pipelines, so 'the same install command' silently deploys a different chart version over time.

  • Using Kustomize's patchesStrategicMerge in a way that unintentionally drops list fields (like container args) since strategic merge patch semantics for lists differ from a naive merge people expect.

  • helm template/helm install rendering cost grows with chart complexity (nested subcharts, heavy template logic) -- very large umbrella charts can noticeably slow CI pipeline render/lint steps.

  • Kustomize's build step re-parses the full overlay+base tree on every invocation -- for very large multi-overlay repos, this can add real seconds to CI; keep overlay trees reasonably shallow.

  • Splitting one giant Helm chart into several smaller, independently-releasable charts reduces blast radius and per-deploy render/diff time compared to one monolithic chart covering an entire platform.

  • Avoid unnecessary Helm subchart dependencies that aren't actually used -- each adds to install/upgrade time and rendered manifest size.

  • Store chart values (especially production values files) in version control alongside application code, reviewed through the same PR process as everything else -- not passed ad hoc on the command line.

  • Use helm upgrade --install --atomic (or equivalent CI wrapping) so a failed upgrade automatically rolls back rather than leaving the release in a broken intermediate state.

  • Keep a documented rollback procedure tested in advance (helm rollback revision numbers, or reapplying a prior Kustomize overlay commit) -- don't discover how rollback works during an incident.

  • Lock Helm chart versions and Kustomize base image tags to specific, reviewed values in production overlays -- never track 'latest' in a production deployment path.

  • Scaffold a Helm chart with helm create, parameterize the replica count via values.yaml, and install it with two different values files producing different replica counts.

  • Run helm rollback after an intentional bad upgrade (e.g. an invalid image tag) and confirm the release returns to the prior working revision.

  • Build a Kustomize base with a Deployment and Service, then create a staging and production overlay that each patch just the replica count and resource limits.

  • Run helm template <chart> | kubectl apply -f - to render a chart to plain manifests, then use that output as the base/ directory for a new Kustomize setup.

  • Helm 3 templates + packages + tracks release lifecycle (install/upgrade/rollback) using per-namespace Secrets.

  • Helm 3 removed Tiller -- all operations use the invoking user's kubeconfig credentials.

  • Kustomize patches plain YAML bases with overlay patches -- no templating, built into kubectl.

  • Helm for packaging reusable software; Kustomize for environment-specific variation.

Want a visual for this concept?

Generate a diagram tailored to “Packaging: Helm 3 & Kustomize” — the AI picks whichever visual (flowchart, comparison, sequence, etc.) best fits.

Sign in to generate a visual →

Practice quiz

Next Step

Continue to Deployment Strategies: Rolling, Blue-Green, Canary & Argo Rollouts← Back to all Kubernetes chapters