rm GetStandardPrinter

pull/8/head
juanvallejo 2018-05-02 14:49:49 -04:00
parent 5a34e4f594
commit a74b28d961
9 changed files with 23 additions and 237 deletions

View File

@ -48,7 +48,7 @@ func NewCmdConfig(f cmdutil.Factory, pathOptions *clientcmd.PathOptions, streams
1. If the --` + pathOptions.ExplicitFileFlag + ` flag is set, then only that file is loaded. The flag may only be set once and no merging takes place.
2. If $` + pathOptions.EnvVar + ` environment variable is set, then it is used a list of paths (normal path delimitting rules for your system). These paths are merged. When a value is modified, it is modified in the file that defines the stanza. When a value is created, it is created in the first file that exists. If no files in the chain exist, then it creates the last file in the list.
3. Otherwise, ` + path.Join("${HOME}", pathOptions.GlobalFileSubpath) + ` is used and no merging takes place.`),
Run: cmdutil.DefaultSubCommandRun(streams.Out),
Run: cmdutil.DefaultSubCommandRun(streams.ErrOut),
}
// file paths are common to all sub commands

View File

@ -22,10 +22,10 @@ import (
"k8s.io/kubernetes/pkg/printers"
)
// PrintFlags composes common printer flag structs
// kubectlConfigPrintFlags composes common printer flag structs
// used across all config commands, and provides a method
// of retrieving a known printer based on flag values provided.
type PrintFlags struct {
type kubectlConfigPrintFlags struct {
JSONYamlPrintFlags *printers.JSONYamlPrintFlags
NamePrintFlags *printers.NamePrintFlags
TemplateFlags *printers.KubeTemplatePrintFlags
@ -33,11 +33,11 @@ type PrintFlags struct {
OutputFormat *string
}
func (f *PrintFlags) Complete(successTemplate string) error {
func (f *kubectlConfigPrintFlags) Complete(successTemplate string) error {
return f.NamePrintFlags.Complete(successTemplate)
}
func (f *PrintFlags) ToPrinter() (printers.ResourcePrinter, error) {
func (f *kubectlConfigPrintFlags) ToPrinter() (printers.ResourcePrinter, error) {
outputFormat := ""
if f.OutputFormat != nil {
outputFormat = *f.OutputFormat
@ -58,34 +58,26 @@ func (f *PrintFlags) ToPrinter() (printers.ResourcePrinter, error) {
return nil, printers.NoCompatiblePrinterError{Options: f}
}
func (f *PrintFlags) AddFlags(cmd *cobra.Command) {
func (f *kubectlConfigPrintFlags) AddFlags(cmd *cobra.Command) {
f.JSONYamlPrintFlags.AddFlags(cmd)
f.NamePrintFlags.AddFlags(cmd)
f.TemplateFlags.AddFlags(cmd)
if f.OutputFormat != nil {
cmd.Flags().StringVarP(f.OutputFormat, "output", "o", *f.OutputFormat, "Output format. One of: json|yaml|wide|name|custom-columns=...|custom-columns-file=...|go-template=...|go-template-file=...|jsonpath=...|jsonpath-file=... See custom columns [http://kubernetes.io/docs/user-guide/kubectl-overview/#custom-columns], golang template [http://golang.org/pkg/text/template/#pkg-overview] and jsonpath template [http://kubernetes.io/docs/user-guide/jsonpath].")
cmd.Flags().StringVarP(f.OutputFormat, "output", "o", *f.OutputFormat, "Output format. One of: json|yaml|name|go-template=...|go-template-file=...|jsonpath=...|jsonpath-file=... See custom columns [http://kubernetes.io/docs/user-guide/kubectl-overview/#custom-columns], golang template [http://golang.org/pkg/text/template/#pkg-overview] and jsonpath template [http://kubernetes.io/docs/user-guide/jsonpath].")
}
}
// WithDefaultOutput sets a default output format if one is not provided through a flag value
func (f *PrintFlags) WithDefaultOutput(output string) *PrintFlags {
existingFormat := ""
if f.OutputFormat != nil {
existingFormat = *f.OutputFormat
}
if len(existingFormat) == 0 {
existingFormat = output
}
f.OutputFormat = &existingFormat
func (f *kubectlConfigPrintFlags) WithDefaultOutput(output string) *kubectlConfigPrintFlags {
f.OutputFormat = &output
return f
}
func NewPrintFlags(operation string) *PrintFlags {
func newKubeConfigPrintFlags(operation string) *kubectlConfigPrintFlags {
outputFormat := ""
return &PrintFlags{
return &kubectlConfigPrintFlags{
OutputFormat: &outputFormat,
JSONYamlPrintFlags: printers.NewJSONYamlPrintFlags(),

View File

@ -33,7 +33,7 @@ import (
)
type ViewOptions struct {
PrintFlags *PrintFlags
PrintFlags *kubectlConfigPrintFlags
PrintObject printers.ResourcePrinterFunc
ConfigAccess clientcmd.ConfigAccess
@ -68,7 +68,7 @@ var (
func NewCmdConfigView(f cmdutil.Factory, streams genericclioptions.IOStreams, ConfigAccess clientcmd.ConfigAccess) *cobra.Command {
o := &ViewOptions{
PrintFlags: NewPrintFlags("").WithDefaultOutput("yaml"),
PrintFlags: newKubeConfigPrintFlags("").WithDefaultOutput("yaml"),
ConfigAccess: ConfigAccess,
IOStreams: streams,

View File

@ -183,9 +183,8 @@ func (o *DeleteOptions) Complete(f cmdutil.Factory, out, errOut io.Writer, args
}
func (o *DeleteOptions) Validate(cmd *cobra.Command) error {
outputMode := cmdutil.GetFlagString(cmd, "output")
if outputMode != "" && outputMode != "name" {
return cmdutil.UsageErrorf(cmd, "Unexpected -o output mode: %v. We only support '-o name'.", outputMode)
if o.Output != "" && o.Output != "name" {
return cmdutil.UsageErrorf(cmd, "Unexpected -o output mode: %v. We only support '-o name'.", o.Output)
}
if o.DeleteAll && len(o.LabelSelector) > 0 {

View File

@ -20,8 +20,6 @@ import (
"fmt"
"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
"k8s.io/kubernetes/pkg/printers"
printersinternal "k8s.io/kubernetes/pkg/printers/internalversion"
)
// SuggestApiResources returns a suggestion to use the "api-resources" command

View File

@ -21,7 +21,6 @@ go_library(
"kube_template_flags.go",
"name.go",
"name_flags.go",
"printers.go",
"tabwriter.go",
"template.go",
"template_flags.go",

View File

@ -91,15 +91,7 @@ func (f *PrintFlags) AddFlags(cmd *cobra.Command) {
// WithDefaultOutput sets a default output format if one is not provided through a flag value
func (f *PrintFlags) WithDefaultOutput(output string) *PrintFlags {
existingFormat := ""
if f.OutputFormat != nil {
existingFormat = *f.OutputFormat
}
if len(existingFormat) == 0 {
existingFormat = output
}
f.OutputFormat = &existingFormat
f.OutputFormat = &output
return f
}

View File

@ -229,78 +229,6 @@ func (obj *TestUnknownType) DeepCopyObject() runtime.Object {
return &clone
}
func TestPrinter(t *testing.T) {
//test inputs
simpleTest := &TestPrintType{"foo"}
podTest := &api.Pod{ObjectMeta: metav1.ObjectMeta{Name: "foo"}}
podListTest := &api.PodList{
Items: []api.Pod{
{ObjectMeta: metav1.ObjectMeta{Name: "foo"}},
{ObjectMeta: metav1.ObjectMeta{Name: "bar"}},
},
}
emptyListTest := &api.PodList{}
testapi, err := legacyscheme.Scheme.ConvertToVersion(podTest, schema.GroupVersion{Group: "", Version: "v1"})
if err != nil {
t.Fatalf("unexpected error: %v", err)
}
printerTests := []struct {
Name string
PrintOpts *printers.PrintOptions
Input runtime.Object
OutputVersions []schema.GroupVersion
Expect string
}{
{"test json", &printers.PrintOptions{OutputFormatType: "json", AllowMissingKeys: true}, simpleTest, nil, "{\n \"Data\": \"foo\"\n}\n"},
{"test yaml", &printers.PrintOptions{OutputFormatType: "yaml", AllowMissingKeys: true}, simpleTest, nil, "Data: foo\n"},
{"test template", &printers.PrintOptions{OutputFormatType: "template", OutputFormatArgument: "{{if .id}}{{.id}}{{end}}{{if .metadata.name}}{{.metadata.name}}{{end}}", AllowMissingKeys: true},
podTest, []schema.GroupVersion{v1.SchemeGroupVersion}, "foo"},
{"test jsonpath", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.metadata.name}", AllowMissingKeys: true}, podTest, []schema.GroupVersion{v1.SchemeGroupVersion}, "foo"},
{"test jsonpath list", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.items[*].metadata.name}", AllowMissingKeys: true}, podListTest, []schema.GroupVersion{v1.SchemeGroupVersion}, "foo bar"},
{"test jsonpath empty list", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.items[*].metadata.name}", AllowMissingKeys: true}, emptyListTest, []schema.GroupVersion{v1.SchemeGroupVersion}, ""},
{"test name", &printers.PrintOptions{OutputFormatType: "name", AllowMissingKeys: true}, podTest, []schema.GroupVersion{v1.SchemeGroupVersion}, "pod/foo\n"},
{"emits versioned objects", &printers.PrintOptions{OutputFormatType: "template", OutputFormatArgument: "{{.kind}}", AllowMissingKeys: true}, testapi, []schema.GroupVersion{v1.SchemeGroupVersion}, "Pod"},
}
for _, test := range printerTests {
buf := bytes.NewBuffer([]byte{})
printer, err := printers.GetStandardPrinter(legacyscheme.Scheme, legacyscheme.Codecs.LegacyCodec(legacyscheme.Registry.RegisteredGroupVersions()...), []runtime.Decoder{legacyscheme.Codecs.UniversalDecoder(), unstructured.UnstructuredJSONScheme}, *test.PrintOpts)
if err != nil {
t.Errorf("in %s, unexpected error: %#v", test.Name, err)
}
if len(test.OutputVersions) > 0 {
printer = printers.NewVersionedPrinter(printer, legacyscheme.Scheme, legacyscheme.Scheme, test.OutputVersions...)
}
if err := printer.PrintObj(test.Input, buf); err != nil {
t.Errorf("in %s, unexpected error: %#v", test.Name, err)
}
if buf.String() != test.Expect {
t.Errorf("in %s, expect %q, got %q", test.Name, test.Expect, buf.String())
}
}
}
func TestBadPrinter(t *testing.T) {
badPrinterTests := []struct {
Name string
PrintOpts *printers.PrintOptions
Error error
}{
{"empty template", &printers.PrintOptions{OutputFormatType: "template", AllowMissingKeys: false}, fmt.Errorf("template format specified but no template given")},
{"bad template", &printers.PrintOptions{OutputFormatType: "template", OutputFormatArgument: "{{ .Name", AllowMissingKeys: false}, fmt.Errorf("error parsing template {{ .Name, template: output:1: unclosed action\n")},
{"bad templatefile", &printers.PrintOptions{OutputFormatType: "templatefile", AllowMissingKeys: false}, fmt.Errorf("template format specified but no template given")},
{"bad jsonpath", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.Name", AllowMissingKeys: false}, fmt.Errorf("error parsing jsonpath {.Name, unclosed action\n")},
{"unknown format", &printers.PrintOptions{OutputFormatType: "anUnknownFormat", OutputFormatArgument: "", AllowMissingKeys: false}, fmt.Errorf("output format \"anUnknownFormat\" not recognized")},
}
for _, test := range badPrinterTests {
_, err := printers.GetStandardPrinter(legacyscheme.Scheme, legacyscheme.Codecs.LegacyCodec(legacyscheme.Registry.RegisteredGroupVersions()...), []runtime.Decoder{legacyscheme.Codecs.UniversalDecoder(), unstructured.UnstructuredJSONScheme}, *test.PrintOpts)
if err == nil || err.Error() != test.Error.Error() {
t.Errorf("in %s, expect %s, got %s", test.Name, test.Error, err)
}
}
}
func testPrinter(t *testing.T, printer printers.ResourcePrinter, unmarshalFunc func(data []byte, v interface{}) error) {
buf := bytes.NewBuffer([]byte{})
@ -471,8 +399,13 @@ func TestNamePrinter(t *testing.T) {
},
"pod/foo\npod/bar\n"},
}
printOpts := &printers.PrintOptions{OutputFormatType: "name", AllowMissingKeys: false}
printer, _ := printers.GetStandardPrinter(legacyscheme.Scheme, legacyscheme.Codecs.LegacyCodec(legacyscheme.Registry.RegisteredGroupVersions()...), []runtime.Decoder{legacyscheme.Codecs.UniversalDecoder(), unstructured.UnstructuredJSONScheme}, *printOpts)
printFlags := printers.NewPrintFlags("").WithDefaultOutput("name")
printer, err := printFlags.ToPrinter()
if err != nil {
t.Fatalf("unexpected err: %v", err)
}
for name, item := range tests {
buff := &bytes.Buffer{}
err := printer.PrintObj(item.obj, buff)
@ -2987,44 +2920,6 @@ func TestPrintPodDisruptionBudget(t *testing.T) {
}
}
func TestAllowMissingKeys(t *testing.T) {
tests := []struct {
Name string
PrintOpts *printers.PrintOptions
Input runtime.Object
Expect string
Error string
}{
{"test template, allow missing keys", &printers.PrintOptions{OutputFormatType: "template", OutputFormatArgument: "{{.blarg}}", AllowMissingKeys: true}, &api.Pod{}, "<no value>", ""},
{"test template, strict", &printers.PrintOptions{OutputFormatType: "template", OutputFormatArgument: "{{.blarg}}", AllowMissingKeys: false}, &api.Pod{}, "", `error executing template "{{.blarg}}": template: output:1:2: executing "output" at <.blarg>: map has no entry for key "blarg"`},
{"test jsonpath, allow missing keys", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.blarg}", AllowMissingKeys: true}, &api.Pod{}, "", ""},
{"test jsonpath, strict", &printers.PrintOptions{OutputFormatType: "jsonpath", OutputFormatArgument: "{.blarg}", AllowMissingKeys: false}, &api.Pod{}, "", "error executing jsonpath \"{.blarg}\": blarg is not found\n"},
}
for _, test := range tests {
buf := bytes.NewBuffer([]byte{})
printer, err := printers.GetStandardPrinter(legacyscheme.Scheme, legacyscheme.Codecs.LegacyCodec(legacyscheme.Registry.RegisteredGroupVersions()...), []runtime.Decoder{legacyscheme.Codecs.UniversalDecoder(), unstructured.UnstructuredJSONScheme}, *test.PrintOpts)
if err != nil {
t.Errorf("in %s, unexpected error: %#v", test.Name, err)
}
err = printer.PrintObj(test.Input, buf)
if len(test.Error) == 0 && err != nil {
t.Errorf("in %s, unexpected error: %v", test.Name, err)
continue
}
if len(test.Error) > 0 {
if err == nil {
t.Errorf("in %s, expected to get error: %v", test.Name, test.Error)
} else if e, a := test.Error, err.Error(); e != a {
t.Errorf("in %s, expected error %q, got %q", test.Name, e, a)
}
continue
}
if buf.String() != test.Expect {
t.Errorf("in %s, expect %q, got %q", test.Name, test.Expect, buf.String())
}
}
}
func TestPrintControllerRevision(t *testing.T) {
tests := []struct {
history apps.ControllerRevision

View File

@ -1,89 +0,0 @@
/*
Copyright 2017 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package printers
import (
"fmt"
"k8s.io/apimachinery/pkg/runtime"
)
// GetStandardPrinter takes a format type, an optional format argument. It will return
// a printer or an error. The printer is agnostic to schema versions, so you must
// send arguments to PrintObj in the version you wish them to be shown using a
// VersionedPrinter (typically when generic is true).
func GetStandardPrinter(typer runtime.ObjectTyper, encoder runtime.Encoder, decoders []runtime.Decoder, options PrintOptions) (ResourcePrinter, error) {
format, formatArgument, allowMissingTemplateKeys := options.OutputFormatType, options.OutputFormatArgument, options.AllowMissingKeys
var printer ResourcePrinter
switch format {
case "json", "yaml":
jsonYamlFlags := NewJSONYamlPrintFlags()
p, err := jsonYamlFlags.ToPrinter(format)
if err != nil {
return nil, err
}
printer = p
case "name":
nameFlags := NewNamePrintFlags("")
namePrinter, err := nameFlags.ToPrinter(format)
if err != nil {
return nil, err
}
printer = namePrinter
case "template", "go-template", "jsonpath", "templatefile", "go-template-file", "jsonpath-file":
// TODO: construct and bind this separately (at the command level)
kubeTemplateFlags := KubeTemplatePrintFlags{
GoTemplatePrintFlags: &GoTemplatePrintFlags{
AllowMissingKeys: &allowMissingTemplateKeys,
TemplateArgument: &formatArgument,
},
JSONPathPrintFlags: &JSONPathPrintFlags{
AllowMissingKeys: &allowMissingTemplateKeys,
TemplateArgument: &formatArgument,
},
}
kubeTemplatePrinter, err := kubeTemplateFlags.ToPrinter(format)
if err != nil {
return nil, err
}
printer = kubeTemplatePrinter
case "custom-columns", "custom-columns-file":
customColumnsFlags := &CustomColumnsPrintFlags{
NoHeaders: options.NoHeaders,
TemplateArgument: formatArgument,
}
customColumnsPrinter, err := customColumnsFlags.ToPrinter(format)
if err != nil {
return nil, err
}
printer = customColumnsPrinter
default:
return nil, fmt.Errorf("output format %q not recognized", format)
}
return printer, nil
}