Ensure the release interface is used in actions instead of the type

Signed-off-by: Matt Farina <matt.farina@suse.com>
pull/31372/head
Matt Farina 7 months ago
parent 9c958dec76
commit a229bf6529

@ -185,7 +185,9 @@ func runInstallForHooksWithSuccess(t *testing.T, manifest, expectedNamespace str
}
vals := map[string]interface{}{}
res, err := instAction.Run(buildChartWithTemplates(templates), vals)
resi, err := instAction.Run(buildChartWithTemplates(templates), vals)
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(expectedOutput, outBuffer.String())
is.Equal(rcommon.StatusDeployed, res.Info.Status)
@ -212,8 +214,10 @@ func runInstallForHooksWithFailure(t *testing.T, manifest, expectedNamespace str
}
vals := map[string]interface{}{}
res, err := instAction.Run(buildChartWithTemplates(templates), vals)
resi, err := instAction.Run(buildChartWithTemplates(templates), vals)
is.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "failed pre-install")
is.Equal(expectedOutput, outBuffer.String())
is.Equal(rcommon.StatusFailed, res.Info.Status)

@ -245,7 +245,7 @@ func (i *Install) installCRDs(crds []chart.CRD) error {
//
// If DryRun is set to true, this will prepare the release, but not install it
func (i *Install) Run(chrt ci.Charter, vals map[string]interface{}) (*release.Release, error) {
func (i *Install) Run(chrt ci.Charter, vals map[string]interface{}) (ri.Releaser, error) {
ctx := context.Background()
return i.RunWithContext(ctx, chrt, vals)
}
@ -254,7 +254,7 @@ func (i *Install) Run(chrt ci.Charter, vals map[string]interface{}) (*release.Re
//
// When the task is cancelled through ctx, the function returns and the install
// proceeds in the background.
func (i *Install) RunWithContext(ctx context.Context, ch ci.Charter, vals map[string]interface{}) (*release.Release, error) {
func (i *Install) RunWithContext(ctx context.Context, ch ci.Charter, vals map[string]interface{}) (ri.Releaser, error) {
var chrt *chart.Chart
switch c := ch.(type) {
case *chart.Chart:

@ -131,10 +131,12 @@ func TestInstallRelease(t *testing.T) {
instAction := installAction(t)
vals := map[string]interface{}{}
ctx, done := context.WithCancel(t.Context())
res, err := instAction.RunWithContext(ctx, buildChart(), vals)
resi, err := instAction.RunWithContext(ctx, buildChart(), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(res.Name, "test-install-release", "Expected release name.")
is.Equal(res.Namespace, "spaced")
@ -181,10 +183,12 @@ func TestInstallReleaseWithTakeOwnership_ResourceNotOwned(t *testing.T) {
config := actionConfigFixtureWithDummyResources(t, createDummyResourceList(false))
instAction := installActionWithConfig(config)
instAction.TakeOwnership = true
res, err := instAction.Run(buildChart(), nil)
resi, err := instAction.Run(buildChart(), nil)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
r, err := instAction.cfg.Releases.Get(res.Name, res.Version)
is.NoError(err)
@ -202,10 +206,12 @@ func TestInstallReleaseWithTakeOwnership_ResourceOwned(t *testing.T) {
config := actionConfigFixtureWithDummyResources(t, createDummyResourceList(true))
instAction := installActionWithConfig(config)
instAction.TakeOwnership = false
res, err := instAction.Run(buildChart(), nil)
resi, err := instAction.Run(buildChart(), nil)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
r, err := instAction.cfg.Releases.Get(res.Name, res.Version)
is.NoError(err)
@ -239,10 +245,12 @@ func TestInstallReleaseWithValues(t *testing.T) {
"simpleKey": "simpleValue",
},
}
res, err := instAction.Run(buildChart(withSampleValues()), userVals)
resi, err := instAction.Run(buildChart(withSampleValues()), userVals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(res.Name, "test-install-release", "Expected release name.")
is.Equal(res.Namespace, "spaced")
@ -280,10 +288,12 @@ func TestInstallRelease_WithNotes(t *testing.T) {
instAction := installAction(t)
instAction.ReleaseName = "with-notes"
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withNotes("note here")), vals)
resi, err := instAction.Run(buildChart(withNotes("note here")), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(res.Name, "with-notes")
is.Equal(res.Namespace, "spaced")
@ -309,10 +319,12 @@ func TestInstallRelease_WithNotesRendered(t *testing.T) {
instAction := installAction(t)
instAction.ReleaseName = "with-notes"
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withNotes("got-{{.Release.Name}}")), vals)
resi, err := instAction.Run(buildChart(withNotes("got-{{.Release.Name}}")), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
r, err := instAction.cfg.Releases.Get(res.Name, res.Version)
is.NoError(err)
@ -330,10 +342,12 @@ func TestInstallRelease_WithChartAndDependencyParentNotes(t *testing.T) {
instAction := installAction(t)
instAction.ReleaseName = "with-notes"
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withNotes("parent"), withDependency(withNotes("child"))), vals)
resi, err := instAction.Run(buildChart(withNotes("parent"), withDependency(withNotes("child"))), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
r, err := instAction.cfg.Releases.Get(res.Name, res.Version)
is.NoError(err)
@ -351,10 +365,12 @@ func TestInstallRelease_WithChartAndDependencyAllNotes(t *testing.T) {
instAction.ReleaseName = "with-notes"
instAction.SubNotes = true
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withNotes("parent"), withDependency(withNotes("child"))), vals)
resi, err := instAction.Run(buildChart(withNotes("parent"), withDependency(withNotes("child"))), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
r, err := instAction.cfg.Releases.Get(res.Name, res.Version)
is.NoError(err)
@ -375,10 +391,12 @@ func TestInstallRelease_DryRunClient(t *testing.T) {
instAction.DryRunStrategy = dryRunStrategy
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withSampleTemplates()), vals)
resi, err := instAction.Run(buildChart(withSampleTemplates()), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Manifest, "---\n# Source: hello/templates/hello\nhello: world")
is.Contains(res.Manifest, "---\n# Source: hello/templates/goodbye\ngoodbye: world")
@ -401,10 +419,12 @@ func TestInstallRelease_DryRunHiddenSecret(t *testing.T) {
// First perform a normal dry-run with the secret and confirm its presence.
instAction.DryRunStrategy = DryRunClient
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(withSampleSecret(), withSampleTemplates()), vals)
resi, err := instAction.Run(buildChart(withSampleSecret(), withSampleTemplates()), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Manifest, "---\n# Source: hello/templates/secret.yaml\napiVersion: v1\nkind: Secret")
_, err = instAction.cfg.Releases.Get(res.Name, res.Version)
@ -414,10 +434,12 @@ func TestInstallRelease_DryRunHiddenSecret(t *testing.T) {
// Perform a dry-run where the secret should not be present
instAction.HideSecret = true
vals = map[string]interface{}{}
res2, err := instAction.Run(buildChart(withSampleSecret(), withSampleTemplates()), vals)
res2i, err := instAction.Run(buildChart(withSampleSecret(), withSampleTemplates()), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res2, err := releaserToV1Release(res2i)
is.NoError(err)
is.NotContains(res2.Manifest, "---\n# Source: hello/templates/secret.yaml\napiVersion: v1\nkind: Secret")
@ -447,10 +469,12 @@ func TestInstallRelease_DryRun_Lookup(t *testing.T) {
Data: []byte(`goodbye: {{ lookup "v1" "Namespace" "" "___" }}`),
})
res, err := instAction.Run(mockChart, vals)
resi, err := instAction.Run(mockChart, vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Manifest, "goodbye: map[]")
}
@ -478,10 +502,12 @@ func TestInstallRelease_NoHooks(t *testing.T) {
instAction.cfg.Releases.Create(releaseStub())
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.True(res.Hooks[0].LastRun.CompletedAt.IsZero(), "hooks should not run with no-hooks")
}
@ -497,8 +523,10 @@ func TestInstallRelease_FailedHooks(t *testing.T) {
failer.PrintingKubeClient = kubefake.PrintingKubeClient{Out: io.Discard, LogOutput: outBuffer}
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
is.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "failed post-install")
is.Equal("", outBuffer.String())
is.Equal(rcommon.StatusFailed, res.Info.Status)
@ -515,7 +543,9 @@ func TestInstallRelease_ReplaceRelease(t *testing.T) {
instAction.ReleaseName = rel.Name
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
// This should have been auto-incremented
@ -556,8 +586,10 @@ func TestInstallRelease_Wait(t *testing.T) {
goroutines := instAction.getGoroutineCount()
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
is.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "I timed out")
is.Equal(res.Info.Status, rcommon.StatusFailed)
@ -597,8 +629,10 @@ func TestInstallRelease_WaitForJobs(t *testing.T) {
instAction.WaitForJobs = true
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
is.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "I timed out")
is.Equal(res.Info.Status, rcommon.StatusFailed)
}
@ -618,11 +652,13 @@ func TestInstallRelease_RollbackOnFailure(t *testing.T) {
instAction.DisableHooks = true
vals := map[string]interface{}{}
res, err := instAction.Run(buildChart(), vals)
resi, err := instAction.Run(buildChart(), vals)
is.Error(err)
is.Contains(err.Error(), "I timed out")
is.Contains(err.Error(), "rollback-on-failure")
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it isn't in storage anymore
_, err = instAction.cfg.Releases.Get(res.Name, res.Version)
is.Error(err)
@ -662,12 +698,14 @@ func TestInstallRelease_RollbackOnFailure_Interrupted(t *testing.T) {
goroutines := instAction.getGoroutineCount()
res, err := instAction.RunWithContext(ctx, buildChart(), vals)
resi, err := instAction.RunWithContext(ctx, buildChart(), vals)
is.Error(err)
is.Contains(err.Error(), "context canceled")
is.Contains(err.Error(), "rollback-on-failure")
is.Contains(err.Error(), "uninstalled")
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it isn't in storage anymore
_, err = instAction.cfg.Releases.Get(res.Name, res.Version)
is.Error(err)
@ -924,10 +962,12 @@ func TestInstallWithLabels(t *testing.T) {
"key1": "val1",
"key2": "val2",
}
res, err := instAction.Run(buildChart(), nil)
resi, err := instAction.Run(buildChart(), nil)
if err != nil {
t.Fatalf("Failed install: %s", err)
}
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(instAction.Labels, res.Labels)
}

@ -21,7 +21,7 @@ import (
"errors"
"helm.sh/helm/v4/pkg/kube"
release "helm.sh/helm/v4/pkg/release/v1"
ri "helm.sh/helm/v4/pkg/release"
)
// Status is the action for checking the deployment status of releases.
@ -45,7 +45,7 @@ func NewStatus(cfg *Configuration) *Status {
}
// Run executes 'helm status' against the given release.
func (s *Status) Run(name string) (*release.Release, error) {
func (s *Status) Run(name string) (ri.Releaser, error) {
if err := s.cfg.KubeClient.IsReachable(); err != nil {
return nil, err
}

@ -36,6 +36,7 @@ import (
"helm.sh/helm/v4/pkg/kube"
"helm.sh/helm/v4/pkg/postrenderer"
"helm.sh/helm/v4/pkg/registry"
ri "helm.sh/helm/v4/pkg/release"
rcommon "helm.sh/helm/v4/pkg/release/common"
release "helm.sh/helm/v4/pkg/release/v1"
releaseutil "helm.sh/helm/v4/pkg/release/v1/util"
@ -152,13 +153,13 @@ func (u *Upgrade) SetRegistryClient(client *registry.Client) {
}
// Run executes the upgrade on the given release.
func (u *Upgrade) Run(name string, chart chart.Charter, vals map[string]interface{}) (*release.Release, error) {
func (u *Upgrade) Run(name string, chart chart.Charter, vals map[string]interface{}) (ri.Releaser, error) {
ctx := context.Background()
return u.RunWithContext(ctx, name, chart, vals)
}
// RunWithContext executes the upgrade on the given release with context.
func (u *Upgrade) RunWithContext(ctx context.Context, name string, ch chart.Charter, vals map[string]interface{}) (*release.Release, error) {
func (u *Upgrade) RunWithContext(ctx context.Context, name string, ch chart.Charter, vals map[string]interface{}) (ri.Releaser, error) {
if err := u.cfg.KubeClient.IsReachable(); err != nil {
return nil, err
}

@ -60,8 +60,10 @@ func TestUpgradeRelease_Success(t *testing.T) {
vals := map[string]interface{}{}
ctx, done := context.WithCancel(t.Context())
res, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
resi, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
req.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(res.Info.Status, common.StatusDeployed)
done()
@ -91,8 +93,10 @@ func TestUpgradeRelease_Wait(t *testing.T) {
upAction.WaitStrategy = kube.StatusWatcherStrategy
vals := map[string]interface{}{}
res, err := upAction.Run(rel.Name, buildChart(), vals)
resi, err := upAction.Run(rel.Name, buildChart(), vals)
req.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "I timed out")
is.Equal(res.Info.Status, common.StatusFailed)
}
@ -114,8 +118,10 @@ func TestUpgradeRelease_WaitForJobs(t *testing.T) {
upAction.WaitForJobs = true
vals := map[string]interface{}{}
res, err := upAction.Run(rel.Name, buildChart(), vals)
resi, err := upAction.Run(rel.Name, buildChart(), vals)
req.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "I timed out")
is.Equal(res.Info.Status, common.StatusFailed)
}
@ -138,9 +144,11 @@ func TestUpgradeRelease_CleanupOnFail(t *testing.T) {
upAction.CleanupOnFail = true
vals := map[string]interface{}{}
res, err := upAction.Run(rel.Name, buildChart(), vals)
resi, err := upAction.Run(rel.Name, buildChart(), vals)
req.Error(err)
is.NotContains(err.Error(), "unable to cleanup resources")
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "I timed out")
is.Equal(res.Info.Status, common.StatusFailed)
}
@ -164,10 +172,12 @@ func TestUpgradeRelease_RollbackOnFailure(t *testing.T) {
upAction.RollbackOnFailure = true
vals := map[string]interface{}{}
res, err := upAction.Run(rel.Name, buildChart(), vals)
resi, err := upAction.Run(rel.Name, buildChart(), vals)
req.Error(err)
is.Contains(err.Error(), "arming key removed")
is.Contains(err.Error(), "rollback-on-failure")
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it is actually upgraded
updatedResi, err := upAction.cfg.Releases.Get(res.Name, 3)
@ -231,7 +241,9 @@ func TestUpgradeRelease_ReuseValues(t *testing.T) {
upAction.ReuseValues = true
// setting newValues and upgrading
res, err := upAction.Run(rel.Name, buildChart(), newValues)
resi, err := upAction.Run(rel.Name, buildChart(), newValues)
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it is actually upgraded
@ -296,7 +308,9 @@ func TestUpgradeRelease_ReuseValues(t *testing.T) {
withMetadataDependency(dependency),
)
// reusing values and upgrading
res, err := upAction.Run(rel.Name, sampleChartWithSubChart, map[string]interface{}{})
resi, err := upAction.Run(rel.Name, sampleChartWithSubChart, map[string]interface{}{})
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now get the upgraded release
@ -358,7 +372,9 @@ func TestUpgradeRelease_ResetThenReuseValues(t *testing.T) {
upAction.ResetThenReuseValues = true
// setting newValues and upgrading
res, err := upAction.Run(rel.Name, buildChart(withValues(newChartValues)), newValues)
resi, err := upAction.Run(rel.Name, buildChart(withValues(newChartValues)), newValues)
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it is actually upgraded
@ -417,9 +433,11 @@ func TestUpgradeRelease_Interrupted_Wait(t *testing.T) {
ctx, cancel := context.WithCancel(t.Context())
time.AfterFunc(time.Second, cancel)
res, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
resi, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
req.Error(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Contains(res.Info.Description, "Upgrade \"interrupted-release\" failed: context canceled")
is.Equal(res.Info.Status, common.StatusFailed)
}
@ -444,11 +462,12 @@ func TestUpgradeRelease_Interrupted_RollbackOnFailure(t *testing.T) {
ctx, cancel := context.WithCancel(t.Context())
time.AfterFunc(time.Second, cancel)
res, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
resi, err := upAction.RunWithContext(ctx, rel.Name, buildChart(), vals)
req.Error(err)
is.Contains(err.Error(), "release interrupted-release failed, and has been rolled back due to rollback-on-failure being set: context canceled")
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it is actually upgraded
updatedResi, err := upAction.cfg.Releases.Get(res.Name, 3)
is.NoError(err)
@ -495,7 +514,9 @@ func TestUpgradeRelease_Labels(t *testing.T) {
"key3": "val3",
}
// setting newValues and upgrading
res, err := upAction.Run(rel.Name, buildChart(), nil)
resi, err := upAction.Run(rel.Name, buildChart(), nil)
is.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
// Now make sure it is actually upgraded and labels were merged
@ -569,9 +590,11 @@ func TestUpgradeRelease_DryRun(t *testing.T) {
vals := map[string]interface{}{}
ctx, done := context.WithCancel(t.Context())
res, err := upAction.RunWithContext(ctx, rel.Name, buildChart(withSampleSecret()), vals)
resi, err := upAction.RunWithContext(ctx, rel.Name, buildChart(withSampleSecret()), vals)
done()
req.NoError(err)
res, err := releaserToV1Release(resi)
is.NoError(err)
is.Equal(common.StatusPendingUpgrade, res.Info.Status)
is.Contains(res.Manifest, "kind: Secret")
@ -587,9 +610,11 @@ func TestUpgradeRelease_DryRun(t *testing.T) {
vals = map[string]interface{}{}
ctx, done = context.WithCancel(t.Context())
res, err = upAction.RunWithContext(ctx, rel.Name, buildChart(withSampleSecret()), vals)
resi, err = upAction.RunWithContext(ctx, rel.Name, buildChart(withSampleSecret()), vals)
done()
req.NoError(err)
res, err = releaserToV1Release(resi)
is.NoError(err)
is.Equal(common.StatusPendingUpgrade, res.Info.Status)
is.NotContains(res.Manifest, "kind: Secret")

@ -323,7 +323,12 @@ func runInstall(args []string, client *action.Install, valueOpts *values.Options
cancel()
}()
return client.RunWithContext(ctx, chartRequested, vals)
ri, err := client.RunWithContext(ctx, chartRequested, vals)
rel, rerr := releaserToV1Release(ri)
if rerr != nil {
return nil, rerr
}
return rel, err
}
// checkIfInstallable validates if a chart can be installed

@ -73,7 +73,11 @@ func newStatusCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
if outfmt == output.Table {
client.ShowResourcesTable = true
}
rel, err := client.Run(args[0])
reli, err := client.Run(args[0])
if err != nil {
return err
}
rel, err := releaserToV1Release(reli)
if err != nil {
return err
}

Loading…
Cancel
Save