mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-07-21 10:51:29 +00:00
Merge pull request #114972 from seans3/remove-openapi-printing
Removes deprecated kubectl openapi column printing
This commit is contained in:
commit
cfa6ad50e6
@ -57,7 +57,6 @@ type GetOptions struct {
|
|||||||
PrintFlags *PrintFlags
|
PrintFlags *PrintFlags
|
||||||
ToPrinter func(*meta.RESTMapping, *bool, bool, bool) (printers.ResourcePrinterFunc, error)
|
ToPrinter func(*meta.RESTMapping, *bool, bool, bool) (printers.ResourcePrinterFunc, error)
|
||||||
IsHumanReadablePrinter bool
|
IsHumanReadablePrinter bool
|
||||||
PrintWithOpenAPICols bool
|
|
||||||
|
|
||||||
CmdParent string
|
CmdParent string
|
||||||
|
|
||||||
@ -137,7 +136,6 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
useOpenAPIPrintColumnFlagLabel = "use-openapi-print-columns"
|
|
||||||
useServerPrintColumns = "server-print"
|
useServerPrintColumns = "server-print"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -184,7 +182,6 @@ func NewCmdGet(parent string, f cmdutil.Factory, streams genericclioptions.IOStr
|
|||||||
cmd.Flags().BoolVar(&o.IgnoreNotFound, "ignore-not-found", o.IgnoreNotFound, "If the requested object does not exist the command will return exit code 0.")
|
cmd.Flags().BoolVar(&o.IgnoreNotFound, "ignore-not-found", o.IgnoreNotFound, "If the requested object does not exist the command will return exit code 0.")
|
||||||
cmd.Flags().StringVar(&o.FieldSelector, "field-selector", o.FieldSelector, "Selector (field query) to filter on, supports '=', '==', and '!='.(e.g. --field-selector key1=value1,key2=value2). The server only supports a limited number of field queries per type.")
|
cmd.Flags().StringVar(&o.FieldSelector, "field-selector", o.FieldSelector, "Selector (field query) to filter on, supports '=', '==', and '!='.(e.g. --field-selector key1=value1,key2=value2). The server only supports a limited number of field queries per type.")
|
||||||
cmd.Flags().BoolVarP(&o.AllNamespaces, "all-namespaces", "A", o.AllNamespaces, "If present, list the requested object(s) across all namespaces. Namespace in current context is ignored even if specified with --namespace.")
|
cmd.Flags().BoolVarP(&o.AllNamespaces, "all-namespaces", "A", o.AllNamespaces, "If present, list the requested object(s) across all namespaces. Namespace in current context is ignored even if specified with --namespace.")
|
||||||
addOpenAPIPrintColumnFlags(cmd, o)
|
|
||||||
addServerPrintColumnFlags(cmd, o)
|
addServerPrintColumnFlags(cmd, o)
|
||||||
cmdutil.AddFilenameOptionFlags(cmd, &o.FilenameOptions, "identifying the resource to get from a server.")
|
cmdutil.AddFilenameOptionFlags(cmd, &o.FilenameOptions, "identifying the resource to get from a server.")
|
||||||
cmdutil.AddChunkSizeFlag(cmd, &o.ChunkSize)
|
cmdutil.AddChunkSizeFlag(cmd, &o.ChunkSize)
|
||||||
@ -241,11 +238,6 @@ func (o *GetOptions) Complete(f cmdutil.Factory, cmd *cobra.Command, args []stri
|
|||||||
printFlags := o.PrintFlags.Copy()
|
printFlags := o.PrintFlags.Copy()
|
||||||
|
|
||||||
if mapping != nil {
|
if mapping != nil {
|
||||||
if !cmdSpecifiesOutputFmt(cmd) && o.PrintWithOpenAPICols {
|
|
||||||
if apiSchema, err := f.OpenAPISchema(); err == nil {
|
|
||||||
printFlags.UseOpenAPIColumns(apiSchema, mapping)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
printFlags.SetKind(mapping.GroupVersionKind.GroupKind())
|
printFlags.SetKind(mapping.GroupVersionKind.GroupKind())
|
||||||
}
|
}
|
||||||
if withNamespace {
|
if withNamespace {
|
||||||
@ -294,11 +286,6 @@ func (o *GetOptions) Complete(f cmdutil.Factory, cmd *cobra.Command, args []stri
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// openapi printing is mutually exclusive with server side printing
|
|
||||||
if o.PrintWithOpenAPICols && o.ServerPrint {
|
|
||||||
fmt.Fprintf(o.IOStreams.ErrOut, "warning: --%s requested, --%s will be ignored\n", useOpenAPIPrintColumnFlagLabel, useServerPrintColumns)
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -433,10 +420,6 @@ func NewRuntimeSorter(objects []runtime.Object, sortBy string) *RuntimeSorter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (o *GetOptions) transformRequests(req *rest.Request) {
|
func (o *GetOptions) transformRequests(req *rest.Request) {
|
||||||
// We need full objects if printing with openapi columns
|
|
||||||
if o.PrintWithOpenAPICols {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
if !o.ServerPrint || !o.IsHumanReadablePrinter {
|
if !o.ServerPrint || !o.IsHumanReadablePrinter {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -580,13 +563,6 @@ func (o *GetOptions) Run(f cmdutil.Factory, cmd *cobra.Command, args []string) e
|
|||||||
lastMapping = mapping
|
lastMapping = mapping
|
||||||
}
|
}
|
||||||
|
|
||||||
// ensure a versioned object is passed to the custom-columns printer
|
|
||||||
// if we are using OpenAPI columns to print
|
|
||||||
if o.PrintWithOpenAPICols {
|
|
||||||
printer.PrintObj(info.Object, w)
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
printer.PrintObj(info.Object, w)
|
printer.PrintObj(info.Object, w)
|
||||||
}
|
}
|
||||||
w.Flush()
|
w.Flush()
|
||||||
@ -830,11 +806,6 @@ func (o *GetOptions) printGeneric(r *resource.Result) error {
|
|||||||
return utilerrors.Reduce(utilerrors.Flatten(utilerrors.NewAggregate(errs)))
|
return utilerrors.Reduce(utilerrors.Flatten(utilerrors.NewAggregate(errs)))
|
||||||
}
|
}
|
||||||
|
|
||||||
func addOpenAPIPrintColumnFlags(cmd *cobra.Command, opt *GetOptions) {
|
|
||||||
cmd.Flags().BoolVar(&opt.PrintWithOpenAPICols, useOpenAPIPrintColumnFlagLabel, opt.PrintWithOpenAPICols, "If true, use x-kubernetes-print-column metadata (if present) from the OpenAPI schema for displaying a resource.")
|
|
||||||
cmd.Flags().MarkDeprecated(useOpenAPIPrintColumnFlagLabel, "deprecated in favor of server-side printing")
|
|
||||||
}
|
|
||||||
|
|
||||||
func addServerPrintColumnFlags(cmd *cobra.Command, opt *GetOptions) {
|
func addServerPrintColumnFlags(cmd *cobra.Command, opt *GetOptions) {
|
||||||
cmd.Flags().BoolVar(&opt.ServerPrint, useServerPrintColumns, opt.ServerPrint, "If true, have the server return the appropriate table output. Supports extension APIs and CRDs.")
|
cmd.Flags().BoolVar(&opt.ServerPrint, useServerPrintColumns, opt.ServerPrint, "If true, have the server return the appropriate table output. Supports extension APIs and CRDs.")
|
||||||
}
|
}
|
||||||
@ -843,10 +814,6 @@ func shouldGetNewPrinterForMapping(printer printers.ResourcePrinter, lastMapping
|
|||||||
return printer == nil || lastMapping == nil || mapping == nil || mapping.Resource != lastMapping.Resource
|
return printer == nil || lastMapping == nil || mapping == nil || mapping.Resource != lastMapping.Resource
|
||||||
}
|
}
|
||||||
|
|
||||||
func cmdSpecifiesOutputFmt(cmd *cobra.Command) bool {
|
|
||||||
return cmdutil.GetFlagString(cmd, "output") != ""
|
|
||||||
}
|
|
||||||
|
|
||||||
func multipleGVKsRequested(infos []*resource.Info) bool {
|
func multipleGVKsRequested(infos []*resource.Info) bool {
|
||||||
if len(infos) < 2 {
|
if len(infos) < 2 {
|
||||||
return false
|
return false
|
||||||
|
@ -22,12 +22,10 @@ import (
|
|||||||
|
|
||||||
"github.com/spf13/cobra"
|
"github.com/spf13/cobra"
|
||||||
|
|
||||||
"k8s.io/apimachinery/pkg/api/meta"
|
|
||||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||||
"k8s.io/cli-runtime/pkg/genericclioptions"
|
"k8s.io/cli-runtime/pkg/genericclioptions"
|
||||||
"k8s.io/cli-runtime/pkg/printers"
|
"k8s.io/cli-runtime/pkg/printers"
|
||||||
"k8s.io/kubectl/pkg/cmd/util"
|
"k8s.io/kubectl/pkg/cmd/util"
|
||||||
"k8s.io/kubectl/pkg/util/openapi"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// PrintFlags composes common printer flag structs
|
// PrintFlags composes common printer flag structs
|
||||||
@ -76,35 +74,6 @@ func (f *PrintFlags) AllowedFormats() []string {
|
|||||||
return formats
|
return formats
|
||||||
}
|
}
|
||||||
|
|
||||||
// UseOpenAPIColumns modifies the output format, as well as the
|
|
||||||
// "allowMissingKeys" option for template printers, to values
|
|
||||||
// defined in the OpenAPI schema of a resource.
|
|
||||||
func (f *PrintFlags) UseOpenAPIColumns(api openapi.Resources, mapping *meta.RESTMapping) error {
|
|
||||||
// Found openapi metadata for this resource
|
|
||||||
schema := api.LookupResource(mapping.GroupVersionKind)
|
|
||||||
if schema == nil {
|
|
||||||
// Schema not found, return empty columns
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
columns, found := openapi.GetPrintColumns(schema.GetExtensions())
|
|
||||||
if !found {
|
|
||||||
// Extension not found, return empty columns
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
parts := strings.SplitN(columns, "=", 2)
|
|
||||||
if len(parts) < 2 {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
allowMissingKeys := true
|
|
||||||
f.OutputFormat = &parts[0]
|
|
||||||
f.TemplateFlags.TemplateArgument = &parts[1]
|
|
||||||
f.TemplateFlags.AllowMissingKeys = &allowMissingKeys
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// ToPrinter attempts to find a composed set of PrintFlags suitable for
|
// ToPrinter attempts to find a composed set of PrintFlags suitable for
|
||||||
// returning a printer based on current flag values.
|
// returning a printer based on current flag values.
|
||||||
func (f *PrintFlags) ToPrinter() (printers.ResourcePrinter, error) {
|
func (f *PrintFlags) ToPrinter() (printers.ResourcePrinter, error) {
|
||||||
|
@ -22,7 +22,6 @@ import (
|
|||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"net/http"
|
"net/http"
|
||||||
"path/filepath"
|
|
||||||
"reflect"
|
"reflect"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
@ -36,7 +35,6 @@ import (
|
|||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
metav1beta1 "k8s.io/apimachinery/pkg/apis/meta/v1beta1"
|
metav1beta1 "k8s.io/apimachinery/pkg/apis/meta/v1beta1"
|
||||||
"k8s.io/apimachinery/pkg/runtime"
|
"k8s.io/apimachinery/pkg/runtime"
|
||||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
|
||||||
"k8s.io/apimachinery/pkg/runtime/serializer/streaming"
|
"k8s.io/apimachinery/pkg/runtime/serializer/streaming"
|
||||||
"k8s.io/apimachinery/pkg/util/diff"
|
"k8s.io/apimachinery/pkg/util/diff"
|
||||||
"k8s.io/apimachinery/pkg/watch"
|
"k8s.io/apimachinery/pkg/watch"
|
||||||
@ -45,11 +43,8 @@ import (
|
|||||||
restclient "k8s.io/client-go/rest"
|
restclient "k8s.io/client-go/rest"
|
||||||
"k8s.io/client-go/rest/fake"
|
"k8s.io/client-go/rest/fake"
|
||||||
restclientwatch "k8s.io/client-go/rest/watch"
|
restclientwatch "k8s.io/client-go/rest/watch"
|
||||||
"k8s.io/kube-openapi/pkg/util/proto"
|
|
||||||
cmdtesting "k8s.io/kubectl/pkg/cmd/testing"
|
cmdtesting "k8s.io/kubectl/pkg/cmd/testing"
|
||||||
"k8s.io/kubectl/pkg/scheme"
|
"k8s.io/kubectl/pkg/scheme"
|
||||||
"k8s.io/kubectl/pkg/util/openapi"
|
|
||||||
openapitesting "k8s.io/kubectl/pkg/util/openapi/testing"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@ -87,11 +82,9 @@ func testComponentStatusData() *corev1.ComponentStatusList {
|
|||||||
// Verifies that schemas that are not in the master tree of Kubernetes can be retrieved via Get.
|
// Verifies that schemas that are not in the master tree of Kubernetes can be retrieved via Get.
|
||||||
func TestGetUnknownSchemaObject(t *testing.T) {
|
func TestGetUnknownSchemaObject(t *testing.T) {
|
||||||
t.Skip("This test is completely broken. The first thing it does is add the object to the scheme!")
|
t.Skip("This test is completely broken. The first thing it does is add the object to the scheme!")
|
||||||
var openapiSchemaPath = filepath.Join("..", "..", "..", "testdata", "openapi", "swagger.json")
|
|
||||||
tf := cmdtesting.NewTestFactory().WithNamespace("test")
|
tf := cmdtesting.NewTestFactory().WithNamespace("test")
|
||||||
defer tf.Cleanup()
|
defer tf.Cleanup()
|
||||||
_, _, codec := cmdtesting.NewExternalScheme()
|
_, _, codec := cmdtesting.NewExternalScheme()
|
||||||
tf.OpenAPISchemaFunc = openapitesting.CreateOpenAPISchemaFunc(openapiSchemaPath)
|
|
||||||
|
|
||||||
obj := &cmdtesting.ExternalType{
|
obj := &cmdtesting.ExternalType{
|
||||||
Kind: "Type",
|
Kind: "Type",
|
||||||
@ -161,67 +154,6 @@ func TestGetSchemaObject(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestGetObjectsWithOpenAPIOutputFormatPresent(t *testing.T) {
|
|
||||||
pods, _, _ := cmdtesting.TestData()
|
|
||||||
|
|
||||||
tf := cmdtesting.NewTestFactory().WithNamespace("test")
|
|
||||||
defer tf.Cleanup()
|
|
||||||
codec := scheme.Codecs.LegacyCodec(scheme.Scheme.PrioritizedVersionsAllGroups()...)
|
|
||||||
|
|
||||||
// override the openAPISchema function to return custom output
|
|
||||||
// for Pod type.
|
|
||||||
tf.OpenAPISchemaFunc = testOpenAPISchemaData
|
|
||||||
tf.UnstructuredClient = &fake.RESTClient{
|
|
||||||
NegotiatedSerializer: resource.UnstructuredPlusDefaultContentConfig().NegotiatedSerializer,
|
|
||||||
Resp: &http.Response{StatusCode: http.StatusOK, Header: cmdtesting.DefaultHeader(), Body: cmdtesting.ObjBody(codec, &pods.Items[0])},
|
|
||||||
}
|
|
||||||
|
|
||||||
streams, _, buf, _ := genericclioptions.NewTestIOStreams()
|
|
||||||
cmd := NewCmdGet("kubectl", tf, streams)
|
|
||||||
cmd.SetOut(buf)
|
|
||||||
cmd.SetErr(buf)
|
|
||||||
cmd.Flags().Set(useOpenAPIPrintColumnFlagLabel, "true")
|
|
||||||
cmd.Run(cmd, []string{"pods", "foo"})
|
|
||||||
|
|
||||||
expected := `NAME RSRC
|
|
||||||
foo 10
|
|
||||||
`
|
|
||||||
if e, a := expected, buf.String(); e != a {
|
|
||||||
t.Errorf("expected\n%v\ngot\n%v", e, a)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
type FakeResources struct {
|
|
||||||
resources map[schema.GroupVersionKind]proto.Schema
|
|
||||||
}
|
|
||||||
|
|
||||||
func (f FakeResources) LookupResource(s schema.GroupVersionKind) proto.Schema {
|
|
||||||
return f.resources[s]
|
|
||||||
}
|
|
||||||
|
|
||||||
func (f FakeResources) GetConsumes(gvk schema.GroupVersionKind, operation string) []string {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
var _ openapi.Resources = &FakeResources{}
|
|
||||||
|
|
||||||
func testOpenAPISchemaData() (openapi.Resources, error) {
|
|
||||||
return &FakeResources{
|
|
||||||
resources: map[schema.GroupVersionKind]proto.Schema{
|
|
||||||
{
|
|
||||||
Version: "v1",
|
|
||||||
Kind: "Pod",
|
|
||||||
}: &proto.Primitive{
|
|
||||||
BaseSchema: proto.BaseSchema{
|
|
||||||
Extensions: map[string]interface{}{
|
|
||||||
"x-kubernetes-print-columns": "custom-columns=NAME:.metadata.name,RSRC:.metadata.resourceVersion",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestGetObjects(t *testing.T) {
|
func TestGetObjects(t *testing.T) {
|
||||||
pods, _, _ := cmdtesting.TestData()
|
pods, _, _ := cmdtesting.TestData()
|
||||||
|
|
||||||
|
@ -1,27 +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 openapi
|
|
||||||
|
|
||||||
import "k8s.io/kube-openapi/pkg/validation/spec"
|
|
||||||
|
|
||||||
// PrintColumnsKey is the key that defines which columns should be printed
|
|
||||||
const PrintColumnsKey = "x-kubernetes-print-columns"
|
|
||||||
|
|
||||||
// GetPrintColumns looks for the open API extension for the display columns.
|
|
||||||
func GetPrintColumns(extensions spec.Extensions) (string, bool) {
|
|
||||||
return extensions.GetString(PrintColumnsKey)
|
|
||||||
}
|
|
Loading…
Reference in New Issue
Block a user