From 23badd4c845a4c32542fc9229381b38c05e09a42 Mon Sep 17 00:00:00 2001 From: Peixuan Ding Date: Sun, 20 Jun 2021 23:25:53 -0400 Subject: [PATCH] Add method for customized box output Signed-off-by: Peixuan Ding --- pkg/minikube/out/out.go | 30 +++++--- pkg/minikube/out/out_test.go | 141 +++++++++++++++++++++++++++++++++++ 2 files changed, 162 insertions(+), 9 deletions(-) diff --git a/pkg/minikube/out/out.go b/pkg/minikube/out/out.go index f2f6f8bc2f..738864c068 100644 --- a/pkg/minikube/out/out.go +++ b/pkg/minikube/out/out.go @@ -68,6 +68,8 @@ var ( JSON = false // spin is spinner showed at starting minikube spin = spinner.New(spinner.CharSets[style.SpinnerCharacter], 100*time.Millisecond) + // defaultBoxCfg is the default style config for cli box output + defaultBoxCfg = box.Config{Py: 1, Px: 4, Type: "Round", Color: "Red"} ) // MaxLogEntries controls the number of log entries to show for each source @@ -113,23 +115,33 @@ func Styled(st style.Enum, format string, a ...V) { } } -func boxedCommon(printFunc func(format string, a ...interface{}), format string, a ...V) { - box := box.New(box.Config{Py: 1, Px: 4, Type: "Round"}) - if useColor { - box.Config.Color = "Red" +func boxedCommon(printFunc func(format string, a ...interface{}), cfg box.Config, title string, format string, a ...V) { + box := box.New(cfg) + if !useColor { + box.Config.Color = "" } str := Sprintf(style.None, format, a...) - printFunc(box.String("", strings.TrimSpace(str))) + printFunc(box.String(title, strings.TrimSpace(str))) } -// Boxed writes a stylized and templated message in a box to stdout +// Boxed writes a stylized and templated message in a box to stdout using the default style config func Boxed(format string, a ...V) { - boxedCommon(String, format, a...) + boxedCommon(String, defaultBoxCfg, "", format, a...) } -// BoxedErr writes a stylized and templated message in a box to stderr +// BoxedErr writes a stylized and templated message in a box to stderr using the default style config func BoxedErr(format string, a ...V) { - boxedCommon(Err, format, a...) + boxedCommon(Err, defaultBoxCfg, "", format, a...) +} + +// BoxedWithConfig writes a templated message in a box with customized style config to stdout +func BoxedWithConfig(cfg box.Config, st style.Enum, title string, format string, a ...V) { + if st != style.None { + title = Sprintf(st, title) + } + // need to make sure no newlines are in the title otherwise box-cli-maker panics + title = strings.ReplaceAll(title, "\n", "") + boxedCommon(String, cfg, title, format, a...) } // Sprintf is used for returning the string (doesn't write anything) diff --git a/pkg/minikube/out/out_test.go b/pkg/minikube/out/out_test.go index 593222350a..ea0f729c8a 100644 --- a/pkg/minikube/out/out_test.go +++ b/pkg/minikube/out/out_test.go @@ -23,6 +23,8 @@ import ( "strconv" "testing" + "github.com/Delta456/box-cli-maker/v2" + "k8s.io/minikube/pkg/minikube/localpath" "k8s.io/minikube/pkg/minikube/style" "k8s.io/minikube/pkg/minikube/tests" @@ -162,3 +164,142 @@ func TestLatestLogPath(t *testing.T) { } } } + +func TestBoxed(t *testing.T) { + f := tests.NewFakeFile() + SetOutFile(f) + Boxed(`Running with {{.driver}} driver and port {{.port}}`, V{"driver": "docker", "port": 8000}) + got := f.String() + want := + `╭────────────────────────────────────────────────╮ +│ │ +│ Running with docker driver and port 8000 │ +│ │ +╰────────────────────────────────────────────────╯ +` + if got != want { + t.Errorf("Boxed() = %q, want %q", got, want) + } +} + +func TestBoxedErr(t *testing.T) { + f := tests.NewFakeFile() + SetErrFile(f) + BoxedErr(`Running with {{.driver}} driver and port {{.port}}`, V{"driver": "docker", "port": 8000}) + got := f.String() + want := + `╭────────────────────────────────────────────────╮ +│ │ +│ Running with docker driver and port 8000 │ +│ │ +╰────────────────────────────────────────────────╯ +` + if got != want { + t.Errorf("Boxed() = %q, want %q", got, want) + } +} + +func TestBoxedWithConfig(t *testing.T) { + testCases := []struct { + config box.Config + st style.Enum + title string + format string + args []V + want string + }{ + { + box.Config{Px: 2, Py: 2}, + style.None, + "", + "Boxed content", + nil, + `┌─────────────────┐ +│ │ +│ │ +│ Boxed content │ +│ │ +│ │ +└─────────────────┘ +`, + }, + { + box.Config{Px: 0, Py: 0}, + style.None, + "", + "Boxed content with 0 padding", + nil, + `┌────────────────────────────┐ +│Boxed content with 0 padding│ +└────────────────────────────┘ +`, + }, + { + box.Config{Px: 1, Py: 1, TitlePos: "Inside"}, + style.None, + "Hello World", + "Boxed content with title inside", + nil, + `┌─────────────────────────────────┐ +│ │ +│ Hello World │ +│ │ +│ Boxed content with title inside │ +│ │ +└─────────────────────────────────┘ +`, + }, + { + box.Config{Px: 1, Py: 1, TitlePos: "Top"}, + style.None, + "Hello World", + "Boxed content with title inside", + nil, + `┌ Hello World ────────────────────┐ +│ │ +│ Boxed content with title inside │ +│ │ +└─────────────────────────────────┘ +`, + }, + { + box.Config{Px: 1, Py: 1, TitlePos: "Top"}, + style.Tip, + "Hello World", + "Boxed content with title inside", + nil, + `┌ * Hello World ──────────────────┐ +│ │ +│ Boxed content with title inside │ +│ │ +└─────────────────────────────────┘ +`, + }, + { + box.Config{Px: 1, Py: 1, TitlePos: "Top"}, + style.Tip, + // This case is to make sure newlines (\n) are removed before printing + // Otherwise box-cli-maker panices: + // https://github.com/Delta456/box-cli-maker/blob/7b5a1ad8a016ce181e7d8b05e24b54ff60b4b38a/box.go#L69-L71 + "Hello \nWorld", + "Boxed content with title inside", + nil, + `┌ * Hello World ──────────────────┐ +│ │ +│ Boxed content with title inside │ +│ │ +└─────────────────────────────────┘ +`, + }, + } + + for _, tc := range testCases { + f := tests.NewFakeFile() + SetOutFile(f) + BoxedWithConfig(tc.config, tc.st, tc.title, tc.format, tc.args...) + got := f.String() + if tc.want != got { + t.Errorf("Expecting BoxedWithConfig(%v, %v, %s, %s, %s) = \n%s, want \n%s", tc.config, tc.st, tc.title, tc.format, tc.args, got, tc.want) + } + } +}