mirror of
https://github.com/ceph/ceph-csi.git
synced 2025-06-13 10:33:35 +00:00
vendor files
This commit is contained in:
57
vendor/k8s.io/kubernetes/pkg/kubectl/explain/BUILD
generated
vendored
Normal file
57
vendor/k8s.io/kubernetes/pkg/kubectl/explain/BUILD
generated
vendored
Normal file
@ -0,0 +1,57 @@
|
||||
load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
|
||||
|
||||
go_library(
|
||||
name = "go_default_library",
|
||||
srcs = [
|
||||
"explain.go",
|
||||
"field_lookup.go",
|
||||
"fields_printer.go",
|
||||
"fields_printer_builder.go",
|
||||
"formatter.go",
|
||||
"model_printer.go",
|
||||
"recursive_fields_printer.go",
|
||||
"typename.go",
|
||||
],
|
||||
importpath = "k8s.io/kubernetes/pkg/kubectl/explain",
|
||||
visibility = ["//visibility:public"],
|
||||
deps = [
|
||||
"//vendor/k8s.io/apimachinery/pkg/api/meta:go_default_library",
|
||||
"//vendor/k8s.io/kube-openapi/pkg/util/proto:go_default_library",
|
||||
],
|
||||
)
|
||||
|
||||
filegroup(
|
||||
name = "package-srcs",
|
||||
srcs = glob(["**"]),
|
||||
tags = ["automanaged"],
|
||||
visibility = ["//visibility:private"],
|
||||
)
|
||||
|
||||
filegroup(
|
||||
name = "all-srcs",
|
||||
srcs = [":package-srcs"],
|
||||
tags = ["automanaged"],
|
||||
visibility = ["//visibility:public"],
|
||||
)
|
||||
|
||||
go_test(
|
||||
name = "go_default_test",
|
||||
srcs = [
|
||||
"explain_test.go",
|
||||
"field_lookup_test.go",
|
||||
"fields_printer_test.go",
|
||||
"formatter_test.go",
|
||||
"model_printer_test.go",
|
||||
"recursive_fields_printer_test.go",
|
||||
"typename_test.go",
|
||||
],
|
||||
data = ["test-swagger.json"],
|
||||
importpath = "k8s.io/kubernetes/pkg/kubectl/explain",
|
||||
library = ":go_default_library",
|
||||
deps = [
|
||||
"//pkg/kubectl/cmd/testing:go_default_library",
|
||||
"//pkg/kubectl/cmd/util/openapi/testing:go_default_library",
|
||||
"//vendor/k8s.io/apimachinery/pkg/api/meta:go_default_library",
|
||||
"//vendor/k8s.io/apimachinery/pkg/runtime/schema:go_default_library",
|
||||
],
|
||||
)
|
4
vendor/k8s.io/kubernetes/pkg/kubectl/explain/OWNERS
generated
vendored
Normal file
4
vendor/k8s.io/kubernetes/pkg/kubectl/explain/OWNERS
generated
vendored
Normal file
@ -0,0 +1,4 @@
|
||||
approvers:
|
||||
- apelisse
|
||||
reviewers:
|
||||
- apelisse
|
68
vendor/k8s.io/kubernetes/pkg/kubectl/explain/explain.go
generated
vendored
Normal file
68
vendor/k8s.io/kubernetes/pkg/kubectl/explain/explain.go
generated
vendored
Normal file
@ -0,0 +1,68 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"io"
|
||||
"strings"
|
||||
|
||||
"k8s.io/apimachinery/pkg/api/meta"
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
)
|
||||
|
||||
type fieldsPrinter interface {
|
||||
PrintFields(proto.Schema) error
|
||||
}
|
||||
|
||||
func splitDotNotation(model string) (string, []string) {
|
||||
var fieldsPath []string
|
||||
|
||||
// ignore trailing period
|
||||
model = strings.TrimSuffix(model, ".")
|
||||
|
||||
dotModel := strings.Split(model, ".")
|
||||
if len(dotModel) >= 1 {
|
||||
fieldsPath = dotModel[1:]
|
||||
}
|
||||
return dotModel[0], fieldsPath
|
||||
}
|
||||
|
||||
// SplitAndParseResourceRequest separates the users input into a model and fields
|
||||
func SplitAndParseResourceRequest(inResource string, mapper meta.RESTMapper) (string, []string, error) {
|
||||
inResource, fieldsPath := splitDotNotation(inResource)
|
||||
inResource, _ = mapper.ResourceSingularizer(inResource)
|
||||
return inResource, fieldsPath, nil
|
||||
}
|
||||
|
||||
// PrintModelDescription prints the description of a specific model or dot path.
|
||||
// If recursive, all components nested within the fields of the schema will be
|
||||
// printed.
|
||||
func PrintModelDescription(fieldsPath []string, w io.Writer, schema proto.Schema, recursive bool) error {
|
||||
fieldName := ""
|
||||
if len(fieldsPath) != 0 {
|
||||
fieldName = fieldsPath[len(fieldsPath)-1]
|
||||
}
|
||||
|
||||
// Go down the fieldsPath to find what we're trying to explain
|
||||
schema, err := LookupSchemaForField(schema, fieldsPath)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
b := fieldsPrinterBuilder{Recursive: recursive}
|
||||
f := &Formatter{Writer: w, Wrap: 80}
|
||||
return PrintModel(fieldName, f, b, schema)
|
||||
}
|
81
vendor/k8s.io/kubernetes/pkg/kubectl/explain/explain_test.go
generated
vendored
Normal file
81
vendor/k8s.io/kubernetes/pkg/kubectl/explain/explain_test.go
generated
vendored
Normal file
@ -0,0 +1,81 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"reflect"
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/api/meta"
|
||||
cmdtesting "k8s.io/kubernetes/pkg/kubectl/cmd/testing"
|
||||
)
|
||||
|
||||
func TestSplitAndParseResourceRequest(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
inresource string
|
||||
|
||||
expectedInResource string
|
||||
expectedFieldsPath []string
|
||||
expectedErr bool
|
||||
}{
|
||||
{
|
||||
name: "no trailing period",
|
||||
inresource: "field1.field2.field3",
|
||||
|
||||
expectedInResource: "field1",
|
||||
expectedFieldsPath: []string{"field2", "field3"},
|
||||
},
|
||||
{
|
||||
name: "trailing period with correct fieldsPath",
|
||||
inresource: "field1.field2.field3.",
|
||||
|
||||
expectedInResource: "field1",
|
||||
expectedFieldsPath: []string{"field2", "field3"},
|
||||
},
|
||||
{
|
||||
name: "trailing period with incorrect fieldsPath",
|
||||
inresource: "field1.field2.field3.",
|
||||
|
||||
expectedInResource: "field1",
|
||||
expectedFieldsPath: []string{"field2", "field3", ""},
|
||||
expectedErr: true,
|
||||
},
|
||||
}
|
||||
|
||||
mapper := getMapper()
|
||||
for _, test := range tests {
|
||||
gotInResource, gotFieldsPath, err := SplitAndParseResourceRequest(test.inresource, mapper)
|
||||
if err != nil {
|
||||
t.Errorf("unexpected error: %v", err)
|
||||
}
|
||||
|
||||
if !reflect.DeepEqual(test.expectedInResource, gotInResource) && !test.expectedErr {
|
||||
t.Errorf("%s: expected inresource: %s, got: %s", test.name, test.expectedInResource, gotInResource)
|
||||
}
|
||||
|
||||
if !reflect.DeepEqual(test.expectedFieldsPath, gotFieldsPath) && !test.expectedErr {
|
||||
t.Errorf("%s: expected fieldsPath: %s, got: %s", test.name, test.expectedFieldsPath, gotFieldsPath)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func getMapper() meta.RESTMapper {
|
||||
f, _, _, _ := cmdtesting.NewTestFactory()
|
||||
mapper, _ := f.Object()
|
||||
return mapper
|
||||
}
|
107
vendor/k8s.io/kubernetes/pkg/kubectl/explain/field_lookup.go
generated
vendored
Normal file
107
vendor/k8s.io/kubernetes/pkg/kubectl/explain/field_lookup.go
generated
vendored
Normal file
@ -0,0 +1,107 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
)
|
||||
|
||||
// fieldLookup walks through a schema by following a path, and returns
|
||||
// the final schema.
|
||||
type fieldLookup struct {
|
||||
// Path to walk
|
||||
Path []string
|
||||
|
||||
// Return information: Schema found, or error.
|
||||
Schema proto.Schema
|
||||
Error error
|
||||
}
|
||||
|
||||
// SaveLeafSchema is used to detect if we are done walking the path, and
|
||||
// saves the schema as a match.
|
||||
func (f *fieldLookup) SaveLeafSchema(schema proto.Schema) bool {
|
||||
if len(f.Path) != 0 {
|
||||
return false
|
||||
}
|
||||
|
||||
f.Schema = schema
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
// VisitArray is mostly a passthrough.
|
||||
func (f *fieldLookup) VisitArray(a *proto.Array) {
|
||||
if f.SaveLeafSchema(a) {
|
||||
return
|
||||
}
|
||||
|
||||
// Passthrough arrays.
|
||||
a.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitMap is mostly a passthrough.
|
||||
func (f *fieldLookup) VisitMap(m *proto.Map) {
|
||||
if f.SaveLeafSchema(m) {
|
||||
return
|
||||
}
|
||||
|
||||
// Passthrough maps.
|
||||
m.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitPrimitive stops the operation and returns itself as the found
|
||||
// schema, even if it had more path to walk.
|
||||
func (f *fieldLookup) VisitPrimitive(p *proto.Primitive) {
|
||||
// Even if Path is not empty (we're not expecting a leaf),
|
||||
// return that primitive.
|
||||
f.Schema = p
|
||||
}
|
||||
|
||||
// VisitKind unstacks fields as it finds them.
|
||||
func (f *fieldLookup) VisitKind(k *proto.Kind) {
|
||||
if f.SaveLeafSchema(k) {
|
||||
return
|
||||
}
|
||||
|
||||
subSchema, ok := k.Fields[f.Path[0]]
|
||||
if !ok {
|
||||
f.Error = fmt.Errorf("field %q does not exist", f.Path[0])
|
||||
return
|
||||
}
|
||||
|
||||
f.Path = f.Path[1:]
|
||||
subSchema.Accept(f)
|
||||
}
|
||||
|
||||
// VisitReference is mostly a passthrough.
|
||||
func (f *fieldLookup) VisitReference(r proto.Reference) {
|
||||
if f.SaveLeafSchema(r) {
|
||||
return
|
||||
}
|
||||
|
||||
// Passthrough references.
|
||||
r.SubSchema().Accept(f)
|
||||
}
|
||||
|
||||
// LookupSchemaForField looks for the schema of a given path in a base schema.
|
||||
func LookupSchemaForField(schema proto.Schema, path []string) (proto.Schema, error) {
|
||||
f := &fieldLookup{Path: path}
|
||||
schema.Accept(f)
|
||||
return f.Schema, f.Error
|
||||
}
|
81
vendor/k8s.io/kubernetes/pkg/kubectl/explain/field_lookup_test.go
generated
vendored
Normal file
81
vendor/k8s.io/kubernetes/pkg/kubectl/explain/field_lookup_test.go
generated
vendored
Normal file
@ -0,0 +1,81 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
)
|
||||
|
||||
func TestFindField(t *testing.T) {
|
||||
schema := resources.LookupResource(schema.GroupVersionKind{
|
||||
Group: "",
|
||||
Version: "v1",
|
||||
Kind: "OneKind",
|
||||
})
|
||||
if schema == nil {
|
||||
t.Fatal("Counldn't find schema v1.OneKind")
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
path []string
|
||||
|
||||
err string
|
||||
expectedPath string
|
||||
}{
|
||||
{
|
||||
path: []string{},
|
||||
expectedPath: "OneKind",
|
||||
},
|
||||
{
|
||||
path: []string{"field1"},
|
||||
expectedPath: "OneKind.field1",
|
||||
},
|
||||
{
|
||||
path: []string{"field1", "array"},
|
||||
expectedPath: "OtherKind.array",
|
||||
},
|
||||
{
|
||||
path: []string{"field1", "what?"},
|
||||
err: `field "what?" does not exist`,
|
||||
},
|
||||
{
|
||||
path: []string{"field1", ""},
|
||||
err: `field "" does not exist`,
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
path, err := LookupSchemaForField(schema, test.path)
|
||||
|
||||
gotErr := ""
|
||||
if err != nil {
|
||||
gotErr = err.Error()
|
||||
}
|
||||
|
||||
gotPath := ""
|
||||
if path != nil {
|
||||
gotPath = path.GetPath().String()
|
||||
}
|
||||
|
||||
if gotErr != test.err || gotPath != test.expectedPath {
|
||||
t.Errorf("LookupSchemaForField(schema, %v) = (path: %q, err: %q), expected (path: %q, err: %q)",
|
||||
test.path, gotPath, gotErr, test.expectedPath, test.err)
|
||||
}
|
||||
}
|
||||
}
|
82
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer.go
generated
vendored
Normal file
82
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer.go
generated
vendored
Normal file
@ -0,0 +1,82 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import "k8s.io/kube-openapi/pkg/util/proto"
|
||||
|
||||
// indentDesc is the level of indentation for descriptions.
|
||||
const indentDesc = 2
|
||||
|
||||
// regularFieldsPrinter prints fields with their type and description.
|
||||
type regularFieldsPrinter struct {
|
||||
Writer *Formatter
|
||||
Error error
|
||||
}
|
||||
|
||||
var _ proto.SchemaVisitor = ®ularFieldsPrinter{}
|
||||
var _ fieldsPrinter = ®ularFieldsPrinter{}
|
||||
|
||||
// VisitArray prints a Array type. It is just a passthrough.
|
||||
func (f *regularFieldsPrinter) VisitArray(a *proto.Array) {
|
||||
a.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitKind prints a Kind type. It prints each key in the kind, with
|
||||
// the type, the required flag, and the description.
|
||||
func (f *regularFieldsPrinter) VisitKind(k *proto.Kind) {
|
||||
for _, key := range k.Keys() {
|
||||
v := k.Fields[key]
|
||||
required := ""
|
||||
if k.IsRequired(key) {
|
||||
required = " -required-"
|
||||
}
|
||||
|
||||
if err := f.Writer.Write("%s\t<%s>%s", key, GetTypeName(v), required); err != nil {
|
||||
f.Error = err
|
||||
return
|
||||
}
|
||||
if err := f.Writer.Indent(indentDesc).WriteWrapped("%s", v.GetDescription()); err != nil {
|
||||
f.Error = err
|
||||
return
|
||||
}
|
||||
if err := f.Writer.Write(""); err != nil {
|
||||
f.Error = err
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// VisitMap prints a Map type. It is just a passthrough.
|
||||
func (f *regularFieldsPrinter) VisitMap(m *proto.Map) {
|
||||
m.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitPrimitive prints a Primitive type. It stops the recursion.
|
||||
func (f *regularFieldsPrinter) VisitPrimitive(p *proto.Primitive) {
|
||||
// Nothing to do. Shouldn't really happen.
|
||||
}
|
||||
|
||||
// VisitReference prints a Reference type. It is just a passthrough.
|
||||
func (f *regularFieldsPrinter) VisitReference(r proto.Reference) {
|
||||
r.SubSchema().Accept(f)
|
||||
}
|
||||
|
||||
// PrintFields will write the types from schema.
|
||||
func (f *regularFieldsPrinter) PrintFields(schema proto.Schema) error {
|
||||
schema.Accept(f)
|
||||
return f.Error
|
||||
}
|
36
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer_builder.go
generated
vendored
Normal file
36
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer_builder.go
generated
vendored
Normal file
@ -0,0 +1,36 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
// fieldsPrinterBuilder builds either a regularFieldsPrinter or a
|
||||
// recursiveFieldsPrinter based on the argument.
|
||||
type fieldsPrinterBuilder struct {
|
||||
Recursive bool
|
||||
}
|
||||
|
||||
// BuildFieldsPrinter builds the appropriate fieldsPrinter.
|
||||
func (f fieldsPrinterBuilder) BuildFieldsPrinter(writer *Formatter) fieldsPrinter {
|
||||
if f.Recursive {
|
||||
return &recursiveFieldsPrinter{
|
||||
Writer: writer,
|
||||
}
|
||||
}
|
||||
|
||||
return ®ularFieldsPrinter{
|
||||
Writer: writer,
|
||||
}
|
||||
}
|
66
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer_test.go
generated
vendored
Normal file
66
vendor/k8s.io/kubernetes/pkg/kubectl/explain/fields_printer_test.go
generated
vendored
Normal file
@ -0,0 +1,66 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
)
|
||||
|
||||
func TestFields(t *testing.T) {
|
||||
schema := resources.LookupResource(schema.GroupVersionKind{
|
||||
Group: "",
|
||||
Version: "v1",
|
||||
Kind: "OneKind",
|
||||
})
|
||||
if schema == nil {
|
||||
t.Fatal("Couldn't find schema v1.OneKind")
|
||||
}
|
||||
|
||||
want := `field1 <Object> -required-
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut lacus ac
|
||||
enim vulputate imperdiet ac accumsan risus. Integer vel accumsan lectus.
|
||||
Praesent tempus nulla id tortor luctus, quis varius nulla laoreet. Ut orci
|
||||
nisi, suscipit id velit sed, blandit eleifend turpis. Curabitur tempus ante at
|
||||
lectus viverra, a mattis augue euismod. Morbi quam ligula, porttitor sit amet
|
||||
lacus non, interdum pulvinar tortor. Praesent accumsan risus et ipsum dictum,
|
||||
vel ullamcorper lorem egestas.
|
||||
|
||||
field2 <[]map[string]string>
|
||||
This is an array of object of PrimitiveDef
|
||||
|
||||
`
|
||||
|
||||
buf := bytes.Buffer{}
|
||||
f := Formatter{
|
||||
Writer: &buf,
|
||||
Wrap: 80,
|
||||
}
|
||||
s, err := LookupSchemaForField(schema, []string{})
|
||||
if err != nil {
|
||||
t.Fatalf("Invalid path %v: %v", []string{}, err)
|
||||
}
|
||||
if err := (fieldsPrinterBuilder{Recursive: false}).BuildFieldsPrinter(&f).PrintFields(s); err != nil {
|
||||
t.Fatalf("Failed to print fields: %v", err)
|
||||
}
|
||||
got := buf.String()
|
||||
if got != want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), want)
|
||||
}
|
||||
}
|
120
vendor/k8s.io/kubernetes/pkg/kubectl/explain/formatter.go
generated
vendored
Normal file
120
vendor/k8s.io/kubernetes/pkg/kubectl/explain/formatter.go
generated
vendored
Normal file
@ -0,0 +1,120 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io"
|
||||
"strings"
|
||||
)
|
||||
|
||||
// Formatter helps you write with indentation, and can wrap text as needed.
|
||||
type Formatter struct {
|
||||
IndentLevel int
|
||||
Wrap int
|
||||
Writer io.Writer
|
||||
}
|
||||
|
||||
// Indent creates a new Formatter that will indent the code by that much more.
|
||||
func (f Formatter) Indent(indent int) *Formatter {
|
||||
f.IndentLevel = f.IndentLevel + indent
|
||||
return &f
|
||||
}
|
||||
|
||||
// Write writes a string with the indentation set for the
|
||||
// Formatter. This is not wrapping text.
|
||||
func (f *Formatter) Write(str string, a ...interface{}) error {
|
||||
// Don't indent empty lines
|
||||
if str == "" {
|
||||
_, err := io.WriteString(f.Writer, "\n")
|
||||
return err
|
||||
}
|
||||
|
||||
indent := ""
|
||||
for i := 0; i < f.IndentLevel; i++ {
|
||||
indent = indent + " "
|
||||
}
|
||||
_, err := io.WriteString(f.Writer, indent+fmt.Sprintf(str, a...)+"\n")
|
||||
return err
|
||||
}
|
||||
|
||||
// WriteWrapped writes a string with the indentation set for the
|
||||
// Formatter, and wraps as needed.
|
||||
func (f *Formatter) WriteWrapped(str string, a ...interface{}) error {
|
||||
if f.Wrap == 0 {
|
||||
return f.Write(str, a...)
|
||||
}
|
||||
text := fmt.Sprintf(str, a...)
|
||||
strs := wrapString(text, f.Wrap-f.IndentLevel)
|
||||
for _, substr := range strs {
|
||||
if err := f.Write(substr); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type line struct {
|
||||
wrap int
|
||||
words []string
|
||||
}
|
||||
|
||||
func (l *line) String() string {
|
||||
return strings.Join(l.words, " ")
|
||||
}
|
||||
|
||||
func (l *line) Empty() bool {
|
||||
return len(l.words) == 0
|
||||
}
|
||||
|
||||
func (l *line) Len() int {
|
||||
return len(l.String())
|
||||
}
|
||||
|
||||
// Add adds the word to the line, returns true if we could, false if we
|
||||
// didn't have enough room. It's always possible to add to an empty line.
|
||||
func (l *line) Add(word string) bool {
|
||||
newLine := line{
|
||||
wrap: l.wrap,
|
||||
words: append(l.words, word),
|
||||
}
|
||||
if newLine.Len() <= l.wrap || len(l.words) == 0 {
|
||||
l.words = newLine.words
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
func wrapString(str string, wrap int) []string {
|
||||
words := strings.Fields(str)
|
||||
wrapped := []string{}
|
||||
l := line{wrap: wrap}
|
||||
|
||||
for _, word := range words {
|
||||
if l.Add(word) == false {
|
||||
wrapped = append(wrapped, l.String())
|
||||
l = line{wrap: wrap}
|
||||
if l.Add(word) == false {
|
||||
panic("Couldn't add to empty line.")
|
||||
}
|
||||
}
|
||||
}
|
||||
if !l.Empty() {
|
||||
wrapped = append(wrapped, l.String())
|
||||
}
|
||||
return wrapped
|
||||
}
|
91
vendor/k8s.io/kubernetes/pkg/kubectl/explain/formatter_test.go
generated
vendored
Normal file
91
vendor/k8s.io/kubernetes/pkg/kubectl/explain/formatter_test.go
generated
vendored
Normal file
@ -0,0 +1,91 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestFormatterWrite(t *testing.T) {
|
||||
buf := bytes.Buffer{}
|
||||
f := Formatter{
|
||||
Writer: &buf,
|
||||
}
|
||||
|
||||
f.Write("Lorem ipsum dolor sit amet, consectetur adipiscing elit.")
|
||||
// Indent creates a new Formatter
|
||||
f.Indent(5).Write("Morbi at turpis faucibus, gravida dolor ut, fringilla velit.")
|
||||
// So Indent(2) doesn't indent to 7 here.
|
||||
f.Indent(2).Write("Etiam maximus urna at tellus faucibus mattis.")
|
||||
|
||||
want := `Lorem ipsum dolor sit amet, consectetur adipiscing elit.
|
||||
Morbi at turpis faucibus, gravida dolor ut, fringilla velit.
|
||||
Etiam maximus urna at tellus faucibus mattis.
|
||||
`
|
||||
|
||||
if buf.String() != want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestFormatterWrappedWrite(t *testing.T) {
|
||||
buf := bytes.Buffer{}
|
||||
f := Formatter{
|
||||
Writer: &buf,
|
||||
Wrap: 50,
|
||||
}
|
||||
|
||||
f.WriteWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi at turpis faucibus, gravida dolor ut, fringilla velit.")
|
||||
f.Indent(10).WriteWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi at turpis faucibus, gravida dolor ut, fringilla velit.")
|
||||
// Test long words (especially urls) on their own line.
|
||||
f.Indent(20).WriteWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit. ThisIsAVeryLongWordThatDoesn'tFitOnALineOnItsOwn. Morbi at turpis faucibus, gravida dolor ut, fringilla velit.")
|
||||
|
||||
want := `Lorem ipsum dolor sit amet, consectetur adipiscing
|
||||
elit. Morbi at turpis faucibus, gravida dolor ut,
|
||||
fringilla velit.
|
||||
Lorem ipsum dolor sit amet, consectetur
|
||||
adipiscing elit. Morbi at turpis
|
||||
faucibus, gravida dolor ut, fringilla
|
||||
velit.
|
||||
Lorem ipsum dolor sit amet,
|
||||
consectetur adipiscing elit.
|
||||
ThisIsAVeryLongWordThatDoesn'tFitOnALineOnItsOwn.
|
||||
Morbi at turpis faucibus,
|
||||
gravida dolor ut, fringilla
|
||||
velit.
|
||||
`
|
||||
|
||||
if buf.String() != want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), want)
|
||||
}
|
||||
}
|
||||
|
||||
func TestDefaultWrap(t *testing.T) {
|
||||
buf := bytes.Buffer{}
|
||||
f := Formatter{
|
||||
Writer: &buf,
|
||||
// Wrap is not set
|
||||
}
|
||||
|
||||
f.WriteWrapped("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi at turpis faucibus, gravida dolor ut, fringilla velit. Etiam maximus urna at tellus faucibus mattis.")
|
||||
want := `Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi at turpis faucibus, gravida dolor ut, fringilla velit. Etiam maximus urna at tellus faucibus mattis.
|
||||
`
|
||||
if buf.String() != want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), want)
|
||||
}
|
||||
}
|
127
vendor/k8s.io/kubernetes/pkg/kubectl/explain/model_printer.go
generated
vendored
Normal file
127
vendor/k8s.io/kubernetes/pkg/kubectl/explain/model_printer.go
generated
vendored
Normal file
@ -0,0 +1,127 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import "k8s.io/kube-openapi/pkg/util/proto"
|
||||
|
||||
// fieldIndentLevel is the level of indentation for fields.
|
||||
const fieldIndentLevel = 3
|
||||
|
||||
// descriptionIndentLevel is the level of indentation for the
|
||||
// description.
|
||||
const descriptionIndentLevel = 5
|
||||
|
||||
// modelPrinter prints a schema in Writer. Its "Builder" will decide if
|
||||
// it's recursive or not.
|
||||
type modelPrinter struct {
|
||||
Name string
|
||||
Type string
|
||||
Descriptions []string
|
||||
Writer *Formatter
|
||||
Builder fieldsPrinterBuilder
|
||||
Error error
|
||||
}
|
||||
|
||||
var _ proto.SchemaVisitor = &modelPrinter{}
|
||||
|
||||
// PrintDescription prints the description for a given schema. There
|
||||
// might be multiple description, since we collect descriptions when we
|
||||
// go through references, arrays and maps.
|
||||
func (m *modelPrinter) PrintDescription(schema proto.Schema) error {
|
||||
if err := m.Writer.Write("DESCRIPTION:"); err != nil {
|
||||
return err
|
||||
}
|
||||
for i, desc := range append(m.Descriptions, schema.GetDescription()) {
|
||||
if desc == "" {
|
||||
continue
|
||||
}
|
||||
if i != 0 {
|
||||
if err := m.Writer.Write(""); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
if err := m.Writer.Indent(descriptionIndentLevel).WriteWrapped(desc); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// VisitArray recurses inside the subtype, while collecting the type if
|
||||
// not done yet, and the description.
|
||||
func (m *modelPrinter) VisitArray(a *proto.Array) {
|
||||
m.Descriptions = append(m.Descriptions, a.GetDescription())
|
||||
if m.Type == "" {
|
||||
m.Type = GetTypeName(a)
|
||||
}
|
||||
a.SubType.Accept(m)
|
||||
}
|
||||
|
||||
// VisitKind prints a full resource with its fields.
|
||||
func (m *modelPrinter) VisitKind(k *proto.Kind) {
|
||||
if m.Type == "" {
|
||||
m.Type = GetTypeName(k)
|
||||
}
|
||||
if m.Name != "" {
|
||||
m.Writer.Write("RESOURCE: %s <%s>\n", m.Name, m.Type)
|
||||
}
|
||||
|
||||
if err := m.PrintDescription(k); err != nil {
|
||||
m.Error = err
|
||||
return
|
||||
}
|
||||
if err := m.Writer.Write("\nFIELDS:"); err != nil {
|
||||
m.Error = err
|
||||
return
|
||||
}
|
||||
m.Error = m.Builder.BuildFieldsPrinter(m.Writer.Indent(fieldIndentLevel)).PrintFields(k)
|
||||
}
|
||||
|
||||
// VisitMap recurses inside the subtype, while collecting the type if
|
||||
// not done yet, and the description.
|
||||
func (m *modelPrinter) VisitMap(om *proto.Map) {
|
||||
m.Descriptions = append(m.Descriptions, om.GetDescription())
|
||||
if m.Type == "" {
|
||||
m.Type = GetTypeName(om)
|
||||
}
|
||||
om.SubType.Accept(m)
|
||||
}
|
||||
|
||||
// VisitPrimitive prints a field type and its description.
|
||||
func (m *modelPrinter) VisitPrimitive(p *proto.Primitive) {
|
||||
if m.Type == "" {
|
||||
m.Type = GetTypeName(p)
|
||||
}
|
||||
if err := m.Writer.Write("FIELD: %s <%s>\n", m.Name, m.Type); err != nil {
|
||||
m.Error = err
|
||||
return
|
||||
}
|
||||
m.Error = m.PrintDescription(p)
|
||||
}
|
||||
|
||||
// VisitReference recurses inside the subtype, while collecting the description.
|
||||
func (m *modelPrinter) VisitReference(r proto.Reference) {
|
||||
m.Descriptions = append(m.Descriptions, r.GetDescription())
|
||||
r.SubSchema().Accept(m)
|
||||
}
|
||||
|
||||
// PrintModel prints the description of a schema in writer.
|
||||
func PrintModel(name string, writer *Formatter, builder fieldsPrinterBuilder, schema proto.Schema) error {
|
||||
m := &modelPrinter{Name: name, Writer: writer, Builder: builder}
|
||||
schema.Accept(m)
|
||||
return m.Error
|
||||
}
|
122
vendor/k8s.io/kubernetes/pkg/kubectl/explain/model_printer_test.go
generated
vendored
Normal file
122
vendor/k8s.io/kubernetes/pkg/kubectl/explain/model_printer_test.go
generated
vendored
Normal file
@ -0,0 +1,122 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
)
|
||||
|
||||
func TestModel(t *testing.T) {
|
||||
schema := resources.LookupResource(schema.GroupVersionKind{
|
||||
Group: "",
|
||||
Version: "v1",
|
||||
Kind: "OneKind",
|
||||
})
|
||||
if schema == nil {
|
||||
t.Fatal("Couldn't find schema v1.OneKind")
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
path []string
|
||||
want string
|
||||
}{
|
||||
{
|
||||
want: `DESCRIPTION:
|
||||
OneKind has a short description
|
||||
|
||||
FIELDS:
|
||||
field1 <Object> -required-
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut lacus ac
|
||||
enim vulputate imperdiet ac accumsan risus. Integer vel accumsan lectus.
|
||||
Praesent tempus nulla id tortor luctus, quis varius nulla laoreet. Ut orci
|
||||
nisi, suscipit id velit sed, blandit eleifend turpis. Curabitur tempus ante
|
||||
at lectus viverra, a mattis augue euismod. Morbi quam ligula, porttitor sit
|
||||
amet lacus non, interdum pulvinar tortor. Praesent accumsan risus et ipsum
|
||||
dictum, vel ullamcorper lorem egestas.
|
||||
|
||||
field2 <[]map[string]string>
|
||||
This is an array of object of PrimitiveDef
|
||||
|
||||
`,
|
||||
path: []string{},
|
||||
},
|
||||
{
|
||||
want: `RESOURCE: field1 <Object>
|
||||
|
||||
DESCRIPTION:
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut lacus ac
|
||||
enim vulputate imperdiet ac accumsan risus. Integer vel accumsan lectus.
|
||||
Praesent tempus nulla id tortor luctus, quis varius nulla laoreet. Ut orci
|
||||
nisi, suscipit id velit sed, blandit eleifend turpis. Curabitur tempus ante
|
||||
at lectus viverra, a mattis augue euismod. Morbi quam ligula, porttitor sit
|
||||
amet lacus non, interdum pulvinar tortor. Praesent accumsan risus et ipsum
|
||||
dictum, vel ullamcorper lorem egestas.
|
||||
|
||||
This is another kind of Kind
|
||||
|
||||
FIELDS:
|
||||
array <[]integer>
|
||||
This array must be an array of int
|
||||
|
||||
int <integer>
|
||||
This int must be an int
|
||||
|
||||
object <map[string]string>
|
||||
This is an object of string
|
||||
|
||||
primitive <string>
|
||||
|
||||
string <string> -required-
|
||||
This string must be a string
|
||||
|
||||
`,
|
||||
path: []string{"field1"},
|
||||
},
|
||||
{
|
||||
want: `FIELD: string <string>
|
||||
|
||||
DESCRIPTION:
|
||||
This string must be a string
|
||||
`,
|
||||
path: []string{"field1", "string"},
|
||||
},
|
||||
{
|
||||
want: `FIELD: array <[]integer>
|
||||
|
||||
DESCRIPTION:
|
||||
This array must be an array of int
|
||||
|
||||
This is an int in an array
|
||||
`,
|
||||
path: []string{"field1", "array"},
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
buf := bytes.Buffer{}
|
||||
if err := PrintModelDescription(test.path, &buf, schema, false); err != nil {
|
||||
t.Fatalf("Failed to PrintModelDescription for path %v: %v", test.path, err)
|
||||
}
|
||||
got := buf.String()
|
||||
if got != test.want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), test.want)
|
||||
}
|
||||
}
|
||||
}
|
75
vendor/k8s.io/kubernetes/pkg/kubectl/explain/recursive_fields_printer.go
generated
vendored
Normal file
75
vendor/k8s.io/kubernetes/pkg/kubectl/explain/recursive_fields_printer.go
generated
vendored
Normal file
@ -0,0 +1,75 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import "k8s.io/kube-openapi/pkg/util/proto"
|
||||
|
||||
// indentPerLevel is the level of indentation for each field recursion.
|
||||
const indentPerLevel = 3
|
||||
|
||||
// recursiveFieldsPrinter recursively prints all the fields for a given
|
||||
// schema.
|
||||
type recursiveFieldsPrinter struct {
|
||||
Writer *Formatter
|
||||
Error error
|
||||
}
|
||||
|
||||
var _ proto.SchemaVisitor = &recursiveFieldsPrinter{}
|
||||
var _ fieldsPrinter = &recursiveFieldsPrinter{}
|
||||
|
||||
// VisitArray is just a passthrough.
|
||||
func (f *recursiveFieldsPrinter) VisitArray(a *proto.Array) {
|
||||
a.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitKind prints all its fields with their type, and then recurses
|
||||
// inside each of these (pre-order).
|
||||
func (f *recursiveFieldsPrinter) VisitKind(k *proto.Kind) {
|
||||
for _, key := range k.Keys() {
|
||||
v := k.Fields[key]
|
||||
f.Writer.Write("%s\t<%s>", key, GetTypeName(v))
|
||||
subFields := &recursiveFieldsPrinter{
|
||||
Writer: f.Writer.Indent(indentPerLevel),
|
||||
}
|
||||
if err := subFields.PrintFields(v); err != nil {
|
||||
f.Error = err
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// VisitMap is just a passthrough.
|
||||
func (f *recursiveFieldsPrinter) VisitMap(m *proto.Map) {
|
||||
m.SubType.Accept(f)
|
||||
}
|
||||
|
||||
// VisitPrimitive does nothing, since it doesn't have sub-fields.
|
||||
func (f *recursiveFieldsPrinter) VisitPrimitive(p *proto.Primitive) {
|
||||
// Nothing to do.
|
||||
}
|
||||
|
||||
// VisitReference is just a passthrough.
|
||||
func (f *recursiveFieldsPrinter) VisitReference(r proto.Reference) {
|
||||
r.SubSchema().Accept(f)
|
||||
}
|
||||
|
||||
// PrintFields will recursively print all the fields for the given
|
||||
// schema.
|
||||
func (f *recursiveFieldsPrinter) PrintFields(schema proto.Schema) error {
|
||||
schema.Accept(f)
|
||||
return f.Error
|
||||
}
|
61
vendor/k8s.io/kubernetes/pkg/kubectl/explain/recursive_fields_printer_test.go
generated
vendored
Normal file
61
vendor/k8s.io/kubernetes/pkg/kubectl/explain/recursive_fields_printer_test.go
generated
vendored
Normal file
@ -0,0 +1,61 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
)
|
||||
|
||||
func TestRecursiveFields(t *testing.T) {
|
||||
schema := resources.LookupResource(schema.GroupVersionKind{
|
||||
Group: "",
|
||||
Version: "v1",
|
||||
Kind: "OneKind",
|
||||
})
|
||||
if schema == nil {
|
||||
t.Fatal("Couldn't find schema v1.OneKind")
|
||||
}
|
||||
|
||||
want := `field1 <Object>
|
||||
array <[]integer>
|
||||
int <integer>
|
||||
object <map[string]string>
|
||||
primitive <string>
|
||||
string <string>
|
||||
field2 <[]map[string]string>
|
||||
`
|
||||
|
||||
buf := bytes.Buffer{}
|
||||
f := Formatter{
|
||||
Writer: &buf,
|
||||
Wrap: 80,
|
||||
}
|
||||
s, err := LookupSchemaForField(schema, []string{})
|
||||
if err != nil {
|
||||
t.Fatalf("Invalid path %v: %v", []string{}, err)
|
||||
}
|
||||
if err := (fieldsPrinterBuilder{Recursive: true}).BuildFieldsPrinter(&f).PrintFields(s); err != nil {
|
||||
t.Fatalf("Failed to print fields: %v", err)
|
||||
}
|
||||
got := buf.String()
|
||||
if got != want {
|
||||
t.Errorf("Got:\n%v\nWant:\n%v\n", buf.String(), want)
|
||||
}
|
||||
}
|
78
vendor/k8s.io/kubernetes/pkg/kubectl/explain/test-swagger.json
generated
vendored
Normal file
78
vendor/k8s.io/kubernetes/pkg/kubectl/explain/test-swagger.json
generated
vendored
Normal file
@ -0,0 +1,78 @@
|
||||
{
|
||||
"swagger": "2.0",
|
||||
"info": {
|
||||
"title": "Kubernetes",
|
||||
"version": "v1.9.0"
|
||||
},
|
||||
"paths": {},
|
||||
"definitions": {
|
||||
"PrimitiveDef": {
|
||||
"type": "string"
|
||||
},
|
||||
"OneKind": {
|
||||
"description": "OneKind has a short description",
|
||||
"required": [
|
||||
"field1",
|
||||
],
|
||||
"properties": {
|
||||
"field1": {
|
||||
"description": "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut lacus ac enim vulputate imperdiet ac accumsan risus. Integer vel accumsan lectus. Praesent tempus nulla id tortor luctus, quis varius nulla laoreet. Ut orci nisi, suscipit id velit sed, blandit eleifend turpis. Curabitur tempus ante at lectus viverra, a mattis augue euismod. Morbi quam ligula, porttitor sit amet lacus non, interdum pulvinar tortor. Praesent accumsan risus et ipsum dictum, vel ullamcorper lorem egestas.",
|
||||
"$ref": "#/definitions/OtherKind"
|
||||
},
|
||||
"field2": {
|
||||
"description": "This is an array of object of PrimitiveDef",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"description": "This is an object of PrimitiveDef",
|
||||
"type": "object",
|
||||
"additionalProperties": {
|
||||
"$ref": "#/definitions/PrimitiveDef"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"x-kubernetes-group-version-kind": [
|
||||
{
|
||||
"group": "",
|
||||
"kind": "OneKind",
|
||||
"version": "v1"
|
||||
}
|
||||
]
|
||||
},
|
||||
"OtherKind": {
|
||||
"description": "This is another kind of Kind",
|
||||
"required": [
|
||||
"string",
|
||||
],
|
||||
"properties": {
|
||||
"string": {
|
||||
"description": "This string must be a string",
|
||||
"type": "string",
|
||||
},
|
||||
"int": {
|
||||
"description": "This int must be an int",
|
||||
"type": "integer",
|
||||
},
|
||||
"array": {
|
||||
"description": "This array must be an array of int",
|
||||
"type": "array",
|
||||
"items": {
|
||||
"description": "This is an int in an array",
|
||||
"type": "integer",
|
||||
}
|
||||
},
|
||||
"object": {
|
||||
"description": "This is an object of string",
|
||||
"type": "object",
|
||||
"additionalProperties": {
|
||||
"description": "this is a string in an object",
|
||||
"type": "string",
|
||||
}
|
||||
},
|
||||
"primitive": {
|
||||
"$ref": "#/definitions/PrimitiveDef"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
66
vendor/k8s.io/kubernetes/pkg/kubectl/explain/typename.go
generated
vendored
Normal file
66
vendor/k8s.io/kubernetes/pkg/kubectl/explain/typename.go
generated
vendored
Normal file
@ -0,0 +1,66 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
)
|
||||
|
||||
// typeName finds the name of a schema
|
||||
type typeName struct {
|
||||
Name string
|
||||
}
|
||||
|
||||
var _ proto.SchemaVisitor = &typeName{}
|
||||
|
||||
// VisitArray adds the [] prefix and recurses.
|
||||
func (t *typeName) VisitArray(a *proto.Array) {
|
||||
s := &typeName{}
|
||||
a.SubType.Accept(s)
|
||||
t.Name = fmt.Sprintf("[]%s", s.Name)
|
||||
}
|
||||
|
||||
// VisitKind just returns "Object".
|
||||
func (t *typeName) VisitKind(k *proto.Kind) {
|
||||
t.Name = "Object"
|
||||
}
|
||||
|
||||
// VisitMap adds the map[string] prefix and recurses.
|
||||
func (t *typeName) VisitMap(m *proto.Map) {
|
||||
s := &typeName{}
|
||||
m.SubType.Accept(s)
|
||||
t.Name = fmt.Sprintf("map[string]%s", s.Name)
|
||||
}
|
||||
|
||||
// VisitPrimitive returns the name of the primitive.
|
||||
func (t *typeName) VisitPrimitive(p *proto.Primitive) {
|
||||
t.Name = p.Type
|
||||
}
|
||||
|
||||
// VisitReference is just a passthrough.
|
||||
func (t *typeName) VisitReference(r proto.Reference) {
|
||||
r.SubSchema().Accept(t)
|
||||
}
|
||||
|
||||
// GetTypeName returns the type of a schema.
|
||||
func GetTypeName(schema proto.Schema) string {
|
||||
t := &typeName{}
|
||||
schema.Accept(t)
|
||||
return t.Name
|
||||
}
|
80
vendor/k8s.io/kubernetes/pkg/kubectl/explain/typename_test.go
generated
vendored
Normal file
80
vendor/k8s.io/kubernetes/pkg/kubectl/explain/typename_test.go
generated
vendored
Normal file
@ -0,0 +1,80 @@
|
||||
/*
|
||||
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 explain
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
tst "k8s.io/kubernetes/pkg/kubectl/cmd/util/openapi/testing"
|
||||
)
|
||||
|
||||
var resources = tst.NewFakeResources("test-swagger.json")
|
||||
|
||||
func TestReferenceTypename(t *testing.T) {
|
||||
schema := resources.LookupResource(schema.GroupVersionKind{
|
||||
Group: "",
|
||||
Version: "v1",
|
||||
Kind: "OneKind",
|
||||
})
|
||||
if schema == nil {
|
||||
t.Fatal("Couldn't find schema v1.OneKind")
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
path []string
|
||||
expected string
|
||||
}{
|
||||
{
|
||||
// Kind is "Object"
|
||||
path: []string{},
|
||||
expected: "Object",
|
||||
},
|
||||
{
|
||||
// Reference is equal to pointed type "Object"
|
||||
path: []string{"field1"},
|
||||
expected: "Object",
|
||||
},
|
||||
{
|
||||
// Reference is equal to pointed type "string"
|
||||
path: []string{"field1", "primitive"},
|
||||
expected: "string",
|
||||
},
|
||||
{
|
||||
// Array of object of reference to string
|
||||
path: []string{"field2"},
|
||||
expected: "[]map[string]string",
|
||||
},
|
||||
{
|
||||
// Array of integer
|
||||
path: []string{"field1", "array"},
|
||||
expected: "[]integer",
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
s, err := LookupSchemaForField(schema, test.path)
|
||||
if err != nil {
|
||||
t.Fatalf("Invalid test.path %v: %v", test.path, err)
|
||||
}
|
||||
got := GetTypeName(s)
|
||||
if got != test.expected {
|
||||
t.Errorf("Got %q, expected %q", got, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user