Skip to content

Reuse existing Helm release values during rad upgrade kubernetes#11361

Open
nicolejms wants to merge 14 commits intoradius-project:mainfrom
nicolejms:pr/auto-from-fork
Open

Reuse existing Helm release values during rad upgrade kubernetes#11361
nicolejms wants to merge 14 commits intoradius-project:mainfrom
nicolejms:pr/auto-from-fork

Conversation

@nicolejms
Copy link
Contributor

@nicolejms nicolejms commented Mar 3, 2026

Description

Today when you upgrade kubernetes, the existing helm values which were used to deploy are ignored. While there is a workaround where you can pass in the helm values, it's counter-intuitive (and hard to troubleshoot failures) to upgrade and lose all existing helm settings. This PR just adds an option to reuse existing values using a built in helm option:

upgradeClient.ReuseValues = true

I reviewed the change with Will Tsai and he agrees this should be the default behavior.

Type of change

  • This pull request fixes a bug in Radius and has an approved issue (issue link required).

Fixes: #11218

Contributor checklist

Please verify that the PR meets the following requirements, where applicable:

  • An overview of proposed schema changes is included in a linked GitHub issue.
    • Yes
    • Not applicable
  • A design document PR is created in the design-notes repository, if new APIs are being introduced.
    • Yes
    • Not applicable
  • The design document has been reviewed and approved by Radius maintainers/approvers.
    • Yes
    • Not applicable
  • A PR for the samples repository is created, if existing samples are affected by the changes in this PR.
    • Yes
    • Not applicable
  • A PR for the documentation repository is created, if the changes in this PR affect the documentation or any user facing updates are made.
    • Yes
    • Not applicable
  • A PR for the recipes repository is created, if existing recipes are affected by the changes in this PR.
    • Yes
    • Not applicable

Copilot AI and others added 14 commits December 12, 2025 21:44
- Changed pkg/cli/helm/cluster.go line 598 to use LastDeployed instead of FirstDeployed
- Updated Test_Helm_GetRadiusRevisions_Success to use different timestamps for different revisions
- Added comprehensive test Test_Helm_GetRadiusRevisions_MultipleUpgradesWithDifferentTimestamps
- All tests pass successfully

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>
…utput

Fix revision timestamps in `rad rollback kubernetes --list-revisions` to show the list of all install times per version.
* Initial plan

* Fix: Use LastDeployed instead of FirstDeployed for revision timestamps

- Changed pkg/cli/helm/cluster.go line 598 to use LastDeployed instead of FirstDeployed
- Updated Test_Helm_GetRadiusRevisions_Success to use different timestamps for different revisions
- Added comprehensive test Test_Helm_GetRadiusRevisions_MultipleUpgradesWithDifferentTimestamps
- All tests pass successfully

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>

* Merge pull request #2 from nicolejms/copilot/fix-revision-timestamp-output

Fix revision timestamps in `rad rollback kubernetes --list-revisions` to show the list of all install times per version.

* Merge branch 'main' into main

* Merge branch 'main' into main

* Merge branch 'radius-project:main' into main

* Merge branch 'radius-project:main' into main

* Merge branch 'radius-project:main' into main

* Merge branch 'radius-project:main' into main

* Merge branch 'radius-project:main' into main

* new agent to investigate issues

* Merge branch 'main' of https://github.com/nicolejms/radius

* Initial plan

* Add ReuseValues flag to Helm upgrade to preserve existing values

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>

* Add test and documentation for value preservation in upgrades

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>

* Address code review feedback with expanded test documentation

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>

* Add integration test to verify ReuseValues preserves existing Helm values

Co-authored-by: nicolejms <101607760+nicolejms@users.noreply.github.com>

* Merge remote-tracking branch 'origin/main' into copilot/fix-issue-11218
@nicolejms nicolejms requested review from a team as code owners March 3, 2026 19:16
Copilot AI review requested due to automatic review settings March 3, 2026 19:16
@nicolejms nicolejms requested a deployment to external-contributor-approval March 3, 2026 19:16 — with GitHub Actions Waiting
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR aims to ensure rad upgrade kubernetes preserves existing Helm release values during upgrades (instead of resetting to chart defaults), and updates CLI help text and tests to reflect/validate that behavior.

Changes:

  • Set ReuseValues=true for Helm upgrades in HelmClientImpl.RunHelmUpgrade.
  • Add a new test intended to validate value preservation/merging during upgrade.
  • Update rad upgrade kubernetes command help text/examples to state that existing values are preserved and merged with --set/--set-file.

Reviewed changes

Copilot reviewed 3 out of 3 changed files in this pull request and generated 4 comments.

File Description
pkg/cli/helm/helmclient.go Enables Helm upgrade value reuse via ReuseValues=true.
pkg/cli/helm/helmclient_test.go Adds a test intended to assert upgrade value preservation/merge behavior.
pkg/cli/cmd/upgrade/kubernetes/kubernetes.go Updates CLI long description/examples to describe preserved/merged Helm values on upgrade.

Comment on lines +117 to +197
// TestHelmClient_UpgradeReusesValues verifies that RunHelmUpgrade preserves existing values
// by using ReuseValues=true. This test validates the fix for issue #11218 where upgrades
// were resetting values to chart defaults.
func TestHelmClient_UpgradeReusesValues(t *testing.T) {
t.Run("upgrade preserves existing values and merges new values", func(t *testing.T) {
// This is an integration test that validates the actual behavior of RunHelmUpgrade
// with ReuseValues=true by simulating an upgrade with Helm's in-memory storage.

// Test data representing values from previous install/upgrade
existingValues := map[string]interface{}{
"global": map[string]interface{}{
"azureWorkloadIdentity": map[string]interface{}{
"enabled": true,
},
"imageRegistry": "myregistry.azurecr.io",
},
"database": map[string]interface{}{
"enabled": true,
},
}

// New values being applied in this upgrade
newValues := map[string]interface{}{
"global": map[string]interface{}{
"imageTag": "0.48.0",
},
}

// Expected merged result: existing values preserved + new values applied
expectedValues := map[string]interface{}{
"global": map[string]interface{}{
"azureWorkloadIdentity": map[string]interface{}{
"enabled": true,
},
"imageRegistry": "myregistry.azurecr.io",
"imageTag": "0.48.0",
},
"database": map[string]interface{}{
"enabled": true,
},
}

// Create an in-memory Helm configuration for testing (similar to Helm's own tests)
registryClient, err := registry.NewClient()
require.NoError(t, err, "Failed to create registry client")

cfg := &helm.Configuration{
Releases: storage.Init(driver.NewMemory()),
KubeClient: &kubefake.PrintingKubeClient{Out: io.Discard},
Capabilities: chartutil.DefaultCapabilities,
RegistryClient: registryClient,
Log: func(format string, v ...interface{}) {},
}

// Create and store an initial release with existing values
initialRelease := &release.Release{
Name: "test-release",
Namespace: "test-namespace",
Version: 1,
Config: existingValues,
Chart: &chart.Chart{
Metadata: &chart.Metadata{
Name: "test-chart",
Version: "1.0.0",
},
},
Info: &release.Info{
Status: release.StatusDeployed,
},
}
err = cfg.Releases.Create(initialRelease)
require.NoError(t, err, "Failed to create initial release")

// Create a chart with new values
upgradeChart := &chart.Chart{
Metadata: &chart.Metadata{
Name: "test-chart",
Version: "1.1.0",
},
Values: newValues,
}
Copy link

Copilot AI Mar 3, 2026

Choose a reason for hiding this comment

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

This test sets upgradeChart.Values to contain only the incremental changes, but in the real codepath helmChart.Values comes from the loaded chart (defaults) and is then mutated by --set/--set-file. That means upgrades will still pass a map containing many default keys, which can overwrite existing release values even with ReuseValues=true. Update the test to reflect the real scenario (chart defaults present) and assert that only CLI overrides are applied on top of the existing release config.

Copilot generated this review using guidance from repository custom instructions.
Copy link
Contributor Author

Choose a reason for hiding this comment

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

@copilot open a new pull request to apply changes based on this feedback

Comment on lines +44 to +47
The upgrade process preserves your existing Helm chart values (such as Azure Workload Identity settings,
database configuration, and custom container registries). The upgrade merges these existing values with
any new values specified via --set or --set-file flags, allowing you to override specific settings
without losing your configuration.
Copy link

Copilot AI Mar 3, 2026

Choose a reason for hiding this comment

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

The command help claims upgrades preserve existing Helm values and only override what’s provided via --set/--set-file, but the current implementation passes helmChart.Values (chart defaults + parsed CLI flags) into Helm upgrade. Unless the upgrade path is changed to pass only user overrides (or an empty map), this documentation is likely inaccurate and may mislead users.

Copilot uses AI. Check for mistakes.
Copy link
Contributor Author

Choose a reason for hiding this comment

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

@copilot open a new pull request to apply changes based on this feedback

Comment on lines 59 to +81
@@ -61,9 +67,18 @@ rad workspace show
rad workspace switch myworkspace
rad upgrade kubernetes

# Upgrade Radius with custom configuration
# Upgrade Radius and override a specific value
# All other existing values from the previous installation are preserved
rad upgrade kubernetes --set key=value

# Example: If you installed with Azure Workload Identity enabled:
# rad install kubernetes --set global.azureWorkloadIdentity.enabled=true
# Then upgrade without repeating the flag - the setting is preserved:
rad upgrade kubernetes

# You can still override specific values during upgrade:
rad upgrade kubernetes --set global.imageTag=0.48

Copy link

Copilot AI Mar 3, 2026

Choose a reason for hiding this comment

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

The examples state that existing values are "automatically preserved" on upgrade, but with the current Helm upgrade invocation this is only true if the values map passed to Helm contains just explicit overrides. Either adjust the implementation to match this behavior or soften the wording in the examples to avoid promising value preservation that may not occur.

Copilot uses AI. Check for mistakes.
Copy link
Contributor Author

Choose a reason for hiding this comment

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

@copilot open a new pull request to apply changes based on this feedback

Comment on lines 96 to 104
upgradeClient := helm.NewUpgrade(helmConf)
upgradeClient.Namespace = namespace
upgradeClient.Wait = wait
upgradeClient.Timeout = upgradeTimeout
upgradeClient.Recreate = true
upgradeClient.ReuseValues = true

return upgradeClient.Run(releaseName, helmChart, helmChart.Values)
}
Copy link

Copilot AI Mar 3, 2026

Choose a reason for hiding this comment

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

Setting upgradeClient.ReuseValues = true won’t preserve prior user configuration as long as you continue to pass helmChart.Values (which includes the chart’s default values plus any --set mutations) into upgradeClient.Run(...). Those defaults will be treated as explicit overrides and can still overwrite the previous release’s config. Consider separating CLI-provided overrides from chart defaults (e.g., build a fresh values map from --set/--set-file and pass only that), or pass an empty values map when no overrides are supplied so reuse-values can actually take effect.

Copilot uses AI. Check for mistakes.
@nicolejms nicolejms changed the title Auto PR from fork: pr/auto-from-fork Reuse existing Helm release values during rad upgrade kubernetes Mar 3, 2026
@codecov
Copy link

codecov bot commented Mar 3, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 51.12%. Comparing base (a1059b6) to head (2f4f956).

Additional details and impacted files
@@            Coverage Diff             @@
##             main   #11361      +/-   ##
==========================================
+ Coverage   51.10%   51.12%   +0.02%     
==========================================
  Files         699      699              
  Lines       44067    44080      +13     
==========================================
+ Hits        22519    22537      +18     
+ Misses      19401    19395       -6     
- Partials     2147     2148       +1     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

rad upgrade kubernetes does not reuse existing Helm release values (resets to chart defaults)

4 participants