fix(cmd): Fix all the outputs

There were two different methods and varying ways to output the status of a release.
This standardizes all of the outputs, but requires a breaking change. Output will
not perfectly match previous v3 output, and we had to break the printing function
in the `action` package, but now things are much more standardized.

Fixes #6238

Signed-off-by: Taylor Thomas <taylor.thomas@microsoft.com>
pull/6550/head
Taylor Thomas 6 years ago
parent 410ec5319f
commit 3799d0024c

@ -58,7 +58,7 @@ func newGetCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
}
return tpl(template, data, out)
}
return printRelease(out, res)
return action.PrintRelease(out, res, true)
},
}

@ -19,6 +19,7 @@ package main
import (
"fmt"
"io"
"time"
"github.com/gosuri/uitable"
"github.com/spf13/cobra"
@ -80,12 +81,12 @@ func newHistoryCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
}
type releaseInfo struct {
Revision int `json:"revision"`
Updated string `json:"updated"`
Status string `json:"status"`
Chart string `json:"chart"`
AppVersion string `json:"app_version"`
Description string `json:"description"`
Revision int `json:"revision"`
Updated time.Time `json:"updated"`
Status string `json:"status"`
Chart string `json:"chart"`
AppVersion string `json:"app_version"`
Description string `json:"description"`
}
type releaseHistory []releaseInfo
@ -102,7 +103,7 @@ func (r releaseHistory) WriteTable(out io.Writer) error {
tbl := uitable.New()
tbl.AddRow("REVISION", "UPDATED", "STATUS", "CHART", "APP VERSION", "DESCRIPTION")
for _, item := range r {
tbl.AddRow(item.Revision, item.Updated, item.Status, item.Chart, item.AppVersion, item.Description)
tbl.AddRow(item.Revision, item.Updated.Format(time.ANSIC), item.Status, item.Chart, item.AppVersion, item.Description)
}
return action.EncodeTable(out, tbl)
}
@ -146,7 +147,7 @@ func getReleaseHistory(rls []*release.Release) (history releaseHistory) {
Description: d,
}
if !r.Info.LastDeployed.IsZero() {
rInfo.Updated = r.Info.LastDeployed.String()
rInfo.Updated = r.Info.LastDeployed
}
history = append(history, rInfo)

@ -123,7 +123,7 @@ func newInstallCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
return err
}
return output.Write(out, &statusPrinter{rel})
return output.Write(out, &statusPrinter{rel, settings.Debug})
},
}

@ -19,59 +19,8 @@ package main
import (
"io"
"text/template"
"time"
"sigs.k8s.io/yaml"
"helm.sh/helm/v3/pkg/chartutil"
"helm.sh/helm/v3/pkg/release"
)
var printReleaseTemplate = `REVISION: {{.Release.Version}}
RELEASED: {{.ReleaseDate}}
CHART: {{.Release.Chart.Metadata.Name}}-{{.Release.Chart.Metadata.Version}}
USER-SUPPLIED VALUES:
{{.Config}}
COMPUTED VALUES:
{{.ComputedValues}}
HOOKS:
{{- range .Release.Hooks }}
---
# {{.Name}}
{{.Manifest}}
{{- end }}
MANIFEST:
{{.Release.Manifest}}
`
func printRelease(out io.Writer, rel *release.Release) error {
if rel == nil {
return nil
}
cfg, err := chartutil.CoalesceValues(rel.Chart, rel.Config)
if err != nil {
return err
}
computed, err := cfg.YAML()
if err != nil {
return err
}
config, err := yaml.Marshal(rel.Config)
if err != nil {
return err
}
data := map[string]interface{}{
"Release": rel,
"Config": string(config),
"ComputedValues": computed,
"ReleaseDate": rel.Info.LastDeployed.Format(time.ANSIC),
}
return tpl(printReleaseTemplate, data, out)
}
func tpl(t string, vals map[string]interface{}, out io.Writer) error {
tt, err := template.New("_").Parse(t)
if err != nil {

@ -61,7 +61,7 @@ func newStatusCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
// strip chart metadata from the output
rel.Chart = nil
return outfmt.Write(out, &statusPrinter{rel})
return outfmt.Write(out, &statusPrinter{rel, false})
},
}
@ -74,6 +74,7 @@ func newStatusCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
type statusPrinter struct {
release *release.Release
debug bool
}
func (s statusPrinter) WriteJSON(out io.Writer) error {
@ -85,6 +86,5 @@ func (s statusPrinter) WriteYAML(out io.Writer) error {
}
func (s statusPrinter) WriteTable(out io.Writer) error {
action.PrintRelease(out, s.release)
return nil
return action.PrintRelease(out, s.release, s.debug)
}

@ -1,6 +1,8 @@
NAME: thomas-guide
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1
RELEASED: Fri Sep 2 22:04:05 1977
CHART: foo-0.1.0-beta.1
USER-SUPPLIED VALUES:
name: value
@ -9,7 +11,7 @@ name: value
HOOKS:
---
# pre-install-hook
# Source: pre-install-hook.yaml
apiVersion: v1
kind: Job
metadata:

@ -1,3 +1,3 @@
REVISION UPDATED STATUS CHART APP VERSION DESCRIPTION
3 1977-09-02 22:04:05 +0000 UTC superseded foo-0.1.0-beta.1 1.0 Release mock
4 1977-09-02 22:04:05 +0000 UTC deployed foo-0.1.0-beta.1 1.0 Release mock
REVISION UPDATED STATUS CHART APP VERSION DESCRIPTION
3 Fri Sep 2 22:04:05 1977 superseded foo-0.1.0-beta.1 1.0 Release mock
4 Fri Sep 2 22:04:05 1977 deployed foo-0.1.0-beta.1 1.0 Release mock

@ -1 +1 @@
[{"revision":3,"updated":"1977-09-02 22:04:05 +0000 UTC","status":"superseded","chart":"foo-0.1.0-beta.1","app_version":"1.0","description":"Release mock"},{"revision":4,"updated":"1977-09-02 22:04:05 +0000 UTC","status":"deployed","chart":"foo-0.1.0-beta.1","app_version":"1.0","description":"Release mock"}]
[{"revision":3,"updated":"1977-09-02T22:04:05Z","status":"superseded","chart":"foo-0.1.0-beta.1","app_version":"1.0","description":"Release mock"},{"revision":4,"updated":"1977-09-02T22:04:05Z","status":"deployed","chart":"foo-0.1.0-beta.1","app_version":"1.0","description":"Release mock"}]

@ -1,5 +1,5 @@
REVISION UPDATED STATUS CHART APP VERSION DESCRIPTION
1 1977-09-02 22:04:05 +0000 UTC superseded foo-0.1.0-beta.1 1.0 Release mock
2 1977-09-02 22:04:05 +0000 UTC superseded foo-0.1.0-beta.1 1.0 Release mock
3 1977-09-02 22:04:05 +0000 UTC superseded foo-0.1.0-beta.1 1.0 Release mock
4 1977-09-02 22:04:05 +0000 UTC deployed foo-0.1.0-beta.1 1.0 Release mock
REVISION UPDATED STATUS CHART APP VERSION DESCRIPTION
1 Fri Sep 2 22:04:05 1977 superseded foo-0.1.0-beta.1 1.0 Release mock
2 Fri Sep 2 22:04:05 1977 superseded foo-0.1.0-beta.1 1.0 Release mock
3 Fri Sep 2 22:04:05 1977 superseded foo-0.1.0-beta.1 1.0 Release mock
4 Fri Sep 2 22:04:05 1977 deployed foo-0.1.0-beta.1 1.0 Release mock

@ -3,10 +3,10 @@
description: Release mock
revision: 3
status: superseded
updated: 1977-09-02 22:04:05 +0000 UTC
updated: "1977-09-02T22:04:05Z"
- app_version: "1.0"
chart: foo-0.1.0-beta.1
description: Release mock
revision: 4
status: deployed
updated: 1977-09-02 22:04:05 +0000 UTC
updated: "1977-09-02T22:04:05Z"

@ -1,4 +1,5 @@
NAME: aeneas
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: FOOBAR
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: aeneas
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: virgil
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: virgil
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: foobar
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: virgil
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: virgil
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: apollo
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: aeneas
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,4 +1,5 @@
NAME: schema
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,6 +1,7 @@
NAME: flummoxed-chickadee
LAST DEPLOYED: 2016-01-16 00:00:00 +0000 UTC
LAST DEPLOYED: Sat Jan 16 00:00:00 2016
NAMESPACE: default
STATUS: deployed
REVISION: 0
NOTES:
release notes

@ -1,14 +1,15 @@
NAME: flummoxed-chickadee
LAST DEPLOYED: 2016-01-16 00:00:00 +0000 UTC
LAST DEPLOYED: Sat Jan 16 00:00:00 2016
NAMESPACE: default
STATUS: deployed
REVISION: 0
TEST SUITE: passing-test
Last Started: 2006-01-02 15:04:05 +0000 UTC
Last Completed: 2006-01-02 15:04:07 +0000 UTC
Last Started: Mon Jan 2 15:04:05 2006
Last Completed: Mon Jan 2 15:04:07 2006
Phase: Succeeded
TEST SUITE: failing-test
Last Started: 2006-01-02 15:10:05 +0000 UTC
Last Completed: 2006-01-02 15:10:07 +0000 UTC
Last Started: Mon Jan 2 15:10:05 2006
Last Completed: Mon Jan 2 15:10:07 2006
Phase: Failed

@ -1,4 +1,5 @@
NAME: flummoxed-chickadee
LAST DEPLOYED: 2016-01-16 00:00:00 +0000 UTC
LAST DEPLOYED: Sat Jan 16 00:00:00 2016
NAMESPACE: default
STATUS: deployed
REVISION: 0

@ -1,4 +1,5 @@
NAME: schema
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 1

@ -1,5 +1,6 @@
Release "crazy-bunny" has been upgraded. Happy Helming!
NAME: crazy-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 2

@ -1,5 +1,6 @@
Release "zany-bunny" has been upgraded. Happy Helming!
NAME: zany-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 2

@ -1,5 +1,6 @@
Release "funny-bunny" has been upgraded. Happy Helming!
NAME: funny-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 5

@ -1,5 +1,6 @@
Release "funny-bunny" has been upgraded. Happy Helming!
NAME: funny-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 6

@ -1,5 +1,6 @@
Release "funny-bunny" has been upgraded. Happy Helming!
NAME: funny-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 4

@ -1,5 +1,6 @@
Release "crazy-bunny" has been upgraded. Happy Helming!
NAME: crazy-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 3

@ -1,5 +1,6 @@
Release "funny-bunny" has been upgraded. Happy Helming!
NAME: funny-bunny
LAST DEPLOYED: 1977-09-02 22:04:05 +0000 UTC
LAST DEPLOYED: Fri Sep 2 22:04:05 1977
NAMESPACE: default
STATUS: deployed
REVISION: 3

@ -99,7 +99,10 @@ func newUpgradeCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
histClient := action.NewHistory(cfg)
histClient.Max = 1
if _, err := histClient.Run(args[0]); err == driver.ErrReleaseNotFound {
fmt.Fprintf(out, "Release %q does not exist. Installing it now.\n", args[0])
// Only print this to stdout for table output
if output == action.Table {
fmt.Fprintf(out, "Release %q does not exist. Installing it now.\n", args[0])
}
instClient := action.NewInstall(cfg)
instClient.ChartPathOptions = client.ChartPathOptions
instClient.DryRun = client.DryRun
@ -114,7 +117,7 @@ func newUpgradeCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
if err != nil {
return err
}
return output.Write(out, &statusPrinter{rel})
return output.Write(out, &statusPrinter{rel, settings.Debug})
}
}
@ -129,27 +132,16 @@ func newUpgradeCmd(cfg *action.Configuration, out io.Writer) *cobra.Command {
}
}
resp, err := client.Run(args[0], ch, vals)
rel, err := client.Run(args[0], ch, vals)
if err != nil {
return errors.Wrap(err, "UPGRADE FAILED")
}
if settings.Debug {
action.PrintRelease(out, resp)
}
if output == action.Table {
fmt.Fprintf(out, "Release %q has been upgraded. Happy Helming!\n", args[0])
}
// Print the status like status command does
statusClient := action.NewStatus(cfg)
rel, err := statusClient.Run(args[0])
if err != nil {
return err
}
return output.Write(out, &statusPrinter{rel})
return output.Write(out, &statusPrinter{rel, settings.Debug})
},
}

@ -20,21 +20,25 @@ import (
"fmt"
"io"
"strings"
"time"
"helm.sh/helm/v3/pkg/chartutil"
"helm.sh/helm/v3/pkg/release"
)
// PrintRelease prints info about a release
func PrintRelease(out io.Writer, rel *release.Release) {
// PrintRelease prints info about a release. If fullInfo is true, it will print
// the user supplied values and the computed values used to render the chart
func PrintRelease(out io.Writer, rel *release.Release, fullInfo bool) error {
if rel == nil {
return
return nil
}
fmt.Fprintf(out, "NAME: %s\n", rel.Name)
if !rel.Info.LastDeployed.IsZero() {
fmt.Fprintf(out, "LAST DEPLOYED: %s\n", rel.Info.LastDeployed)
fmt.Fprintf(out, "LAST DEPLOYED: %s\n", rel.Info.LastDeployed.Format(time.ANSIC))
}
fmt.Fprintf(out, "NAMESPACE: %s\n", rel.Namespace)
fmt.Fprintf(out, "STATUS: %s\n", rel.Info.Status.String())
fmt.Fprintf(out, "REVISION: %d\n", rel.Version)
executions := executionsByHookEvent(rel)
if tests, ok := executions[release.HookTest]; ok {
@ -45,20 +49,48 @@ func PrintRelease(out io.Writer, rel *release.Release) {
}
fmt.Fprintf(out, "TEST SUITE: %s\n%s\n%s\n%s\n\n",
h.Name,
fmt.Sprintf("Last Started: %s", h.LastRun.StartedAt),
fmt.Sprintf("Last Completed: %s", h.LastRun.CompletedAt),
fmt.Sprintf("Last Started: %s", h.LastRun.StartedAt.Format(time.ANSIC)),
fmt.Sprintf("Last Completed: %s", h.LastRun.CompletedAt.Format(time.ANSIC)),
fmt.Sprintf("Phase: %s", h.LastRun.Phase),
)
}
}
if strings.EqualFold(rel.Info.Description, "Dry run complete") {
if fullInfo {
fmt.Fprintln(out, "USER-SUPPLIED VALUES:")
err := EncodeYAML(out, rel.Config)
if err != nil {
return err
}
// Print an extra newline
fmt.Fprintln(out)
cfg, err := chartutil.CoalesceValues(rel.Chart, rel.Config)
if err != nil {
return err
}
fmt.Fprintln(out, "COMPUTED VALUES:")
err = EncodeYAML(out, cfg.AsMap())
if err != nil {
return err
}
// Print an extra newline
fmt.Fprintln(out)
}
if strings.EqualFold(rel.Info.Description, "Dry run complete") || fullInfo {
fmt.Fprintln(out, "HOOKS:")
for _, h := range rel.Hooks {
fmt.Fprintf(out, "---\n# Source: %s\n%s\n", h.Path, h.Manifest)
}
fmt.Fprintf(out, "MANIFEST:\n%s\n", rel.Manifest)
}
if len(rel.Info.Notes) > 0 {
fmt.Fprintf(out, "NOTES:\n%s\n", strings.TrimSpace(rel.Info.Notes))
}
return nil
}
func executionsByHookEvent(rel *release.Release) map[release.HookEvent][]*release.Hook {

Loading…
Cancel
Save