mirror of
https://github.com/ceph/ceph-csi.git
synced 2025-06-13 18:43:34 +00:00
vendor files
This commit is contained in:
53
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/BUILD
generated
vendored
Normal file
53
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/BUILD
generated
vendored
Normal file
@ -0,0 +1,53 @@
|
||||
load("@io_bazel_rules_go//go:def.bzl", "go_library", "go_test")
|
||||
|
||||
go_library(
|
||||
name = "go_default_library",
|
||||
srcs = [
|
||||
"factory.go",
|
||||
"item.go",
|
||||
"list_element.go",
|
||||
"map_element.go",
|
||||
"openapi.go",
|
||||
"primitive_element.go",
|
||||
"type_element.go",
|
||||
"util.go",
|
||||
"visitor.go",
|
||||
],
|
||||
importpath = "k8s.io/kubernetes/pkg/kubectl/apply/parse",
|
||||
visibility = ["//visibility:public"],
|
||||
deps = [
|
||||
"//pkg/kubectl/apply:go_default_library",
|
||||
"//pkg/kubectl/cmd/util/openapi:go_default_library",
|
||||
"//vendor/k8s.io/apimachinery/pkg/runtime/schema:go_default_library",
|
||||
"//vendor/k8s.io/kube-openapi/pkg/util/proto:go_default_library",
|
||||
],
|
||||
)
|
||||
|
||||
go_test(
|
||||
name = "go_default_xtest",
|
||||
srcs = ["suite_test.go"],
|
||||
data = [
|
||||
"//api/openapi-spec:swagger-spec",
|
||||
],
|
||||
importpath = "k8s.io/kubernetes/pkg/kubectl/apply/parse_test",
|
||||
deps = [
|
||||
"//vendor/github.com/onsi/ginkgo:go_default_library",
|
||||
"//vendor/github.com/onsi/ginkgo/config:go_default_library",
|
||||
"//vendor/github.com/onsi/ginkgo/types:go_default_library",
|
||||
"//vendor/github.com/onsi/gomega: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"],
|
||||
)
|
120
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/factory.go
generated
vendored
Normal file
120
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/factory.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 parse
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
"k8s.io/kubernetes/pkg/kubectl/cmd/util/openapi"
|
||||
)
|
||||
|
||||
// Factory creates an Element by combining object values from recorded, local and remote sources with
|
||||
// the metadata from an openapi schema.
|
||||
type Factory struct {
|
||||
// Resources contains the openapi field metadata for the object models
|
||||
Resources openapi.Resources
|
||||
}
|
||||
|
||||
// CreateElement returns an Element by collating the recorded, local and remote field values
|
||||
func (b *Factory) CreateElement(recorded, local, remote map[string]interface{}) (apply.Element, error) {
|
||||
// Create an Item from the 3 values. Use empty name for field
|
||||
visitor := &ElementBuildingVisitor{b.Resources}
|
||||
|
||||
gvk, err := getCommonGroupVersionKind(recorded, local, remote)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Get the openapi object metadata
|
||||
s := visitor.resources.LookupResource(gvk)
|
||||
oapiKind, err := getKind(s)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
data := apply.NewRawElementData(recorded, local, remote)
|
||||
fieldName := ""
|
||||
item, err := visitor.getItem(oapiKind, fieldName, data)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Collate each field of the item into a combined Element
|
||||
return item.CreateElement(visitor)
|
||||
}
|
||||
|
||||
// getItem returns the appropriate Item based on the underlying type of the arguments
|
||||
func (v *ElementBuildingVisitor) getItem(s proto.Schema, name string, data apply.RawElementData) (Item, error) {
|
||||
kind, err := getType(data.GetRecorded(), data.GetLocal(), data.GetRemote())
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if kind == nil {
|
||||
// All of the items values are nil.
|
||||
return &emptyItem{Name: name}, nil
|
||||
}
|
||||
|
||||
// Create an item matching the type
|
||||
switch kind.Kind() {
|
||||
case reflect.Bool, reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Uint,
|
||||
reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Float32, reflect.Float64,
|
||||
reflect.String:
|
||||
p, err := getPrimitive(s)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("expected openapi Primitive, was %T for %v (%v)", s, kind, err)
|
||||
}
|
||||
return &primitiveItem{name, p, data}, nil
|
||||
case reflect.Array, reflect.Slice:
|
||||
a, err := getArray(s)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("expected openapi Array, was %T for %v (%v)", s, kind, err)
|
||||
}
|
||||
return &listItem{
|
||||
Name: name,
|
||||
Array: a,
|
||||
ListElementData: apply.ListElementData{
|
||||
RawElementData: data,
|
||||
},
|
||||
}, nil
|
||||
case reflect.Map:
|
||||
if k, err := getKind(s); err == nil {
|
||||
return &typeItem{
|
||||
Name: name,
|
||||
Type: k,
|
||||
MapElementData: apply.MapElementData{
|
||||
RawElementData: data,
|
||||
},
|
||||
}, nil
|
||||
}
|
||||
// If it looks like a map, and no openapi type is found, default to mapItem
|
||||
m, err := getMap(s)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("expected openapi Kind or Map, was %T for %v (%v)", s, kind, err)
|
||||
}
|
||||
return &mapItem{
|
||||
Name: name,
|
||||
Map: m,
|
||||
MapElementData: apply.MapElementData{
|
||||
RawElementData: data,
|
||||
},
|
||||
}, nil
|
||||
}
|
||||
return nil, fmt.Errorf("unsupported type type %v", kind)
|
||||
}
|
120
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/item.go
generated
vendored
Normal file
120
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/item.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 parse
|
||||
|
||||
import (
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
)
|
||||
|
||||
// Item wraps values from 3 sources (recorded, local, remote).
|
||||
// The values are not collated
|
||||
type Item interface {
|
||||
// CreateElement merges the values in the item into a combined Element
|
||||
CreateElement(ItemVisitor) (apply.Element, error)
|
||||
}
|
||||
|
||||
// primitiveItem contains a recorded, local, and remote value
|
||||
type primitiveItem struct {
|
||||
Name string
|
||||
Primitive *proto.Primitive
|
||||
|
||||
apply.RawElementData
|
||||
}
|
||||
|
||||
func (i *primitiveItem) CreateElement(v ItemVisitor) (apply.Element, error) {
|
||||
return v.CreatePrimitiveElement(i)
|
||||
}
|
||||
|
||||
func (i *primitiveItem) GetMeta() proto.Schema {
|
||||
// https://golang.org/doc/faq#nil_error
|
||||
if i.Primitive != nil {
|
||||
return i.Primitive
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// listItem contains a recorded, local, and remote list
|
||||
type listItem struct {
|
||||
Name string
|
||||
Array *proto.Array
|
||||
|
||||
apply.ListElementData
|
||||
}
|
||||
|
||||
func (i *listItem) CreateElement(v ItemVisitor) (apply.Element, error) {
|
||||
return v.CreateListElement(i)
|
||||
}
|
||||
|
||||
func (i *listItem) GetMeta() proto.Schema {
|
||||
// https://golang.org/doc/faq#nil_error
|
||||
if i.Array != nil {
|
||||
return i.Array
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// mapItem contains a recorded, local, and remote map
|
||||
type mapItem struct {
|
||||
Name string
|
||||
Map *proto.Map
|
||||
|
||||
apply.MapElementData
|
||||
}
|
||||
|
||||
func (i *mapItem) CreateElement(v ItemVisitor) (apply.Element, error) {
|
||||
return v.CreateMapElement(i)
|
||||
}
|
||||
|
||||
func (i *mapItem) GetMeta() proto.Schema {
|
||||
// https://golang.org/doc/faq#nil_error
|
||||
if i.Map != nil {
|
||||
return i.Map
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// mapItem contains a recorded, local, and remote map
|
||||
type typeItem struct {
|
||||
Name string
|
||||
Type *proto.Kind
|
||||
|
||||
apply.MapElementData
|
||||
}
|
||||
|
||||
func (i *typeItem) GetMeta() proto.Schema {
|
||||
// https://golang.org/doc/faq#nil_error
|
||||
if i.Type != nil {
|
||||
return i.Type
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (i *typeItem) CreateElement(v ItemVisitor) (apply.Element, error) {
|
||||
return v.CreateTypeElement(i)
|
||||
}
|
||||
|
||||
// emptyItem contains no values
|
||||
type emptyItem struct {
|
||||
Name string
|
||||
}
|
||||
|
||||
func (i *emptyItem) CreateElement(v ItemVisitor) (apply.Element, error) {
|
||||
e := &apply.EmptyElement{}
|
||||
e.Name = i.Name
|
||||
return e, nil
|
||||
}
|
199
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/list_element.go
generated
vendored
Normal file
199
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/list_element.go
generated
vendored
Normal file
@ -0,0 +1,199 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
)
|
||||
|
||||
// Contains the heavy lifting for finding tuples of matching elements in lists based on the merge key
|
||||
// and then uses the canonical order derived from the orders in the recorded, local and remote lists.
|
||||
|
||||
// replaceListElement builds a ListElement for a listItem.
|
||||
// Uses the "merge" strategy to identify "same" elements across lists by a "merge key"
|
||||
func (v ElementBuildingVisitor) mergeListElement(meta apply.FieldMetaImpl, item *listItem) (*apply.ListElement, error) {
|
||||
subtype := getSchemaType(item.Array.SubType)
|
||||
switch subtype {
|
||||
case "primitive":
|
||||
return v.doPrimitiveList(meta, item)
|
||||
case "map", "kind", "reference":
|
||||
return v.doMapList(meta, item)
|
||||
default:
|
||||
return nil, fmt.Errorf("Cannot merge lists with subtype %s", subtype)
|
||||
}
|
||||
}
|
||||
|
||||
// doPrimitiveList merges 3 lists of primitives together
|
||||
// tries to maintain ordering
|
||||
func (v ElementBuildingVisitor) doPrimitiveList(meta apply.FieldMetaImpl, item *listItem) (*apply.ListElement, error) {
|
||||
result := &apply.ListElement{
|
||||
FieldMetaImpl: apply.FieldMetaImpl{
|
||||
MergeType: apply.MergeStrategy,
|
||||
Name: item.Name,
|
||||
},
|
||||
ListElementData: item.ListElementData,
|
||||
Values: []apply.Element{},
|
||||
}
|
||||
|
||||
// Use locally defined order, then add remote, then add recorded.
|
||||
orderedKeys := &apply.CombinedPrimitiveSlice{}
|
||||
|
||||
// Locally defined items come first and retain their order
|
||||
// as defined locally
|
||||
for _, l := range item.GetLocalList() {
|
||||
orderedKeys.UpsertLocal(l)
|
||||
}
|
||||
// Mixin remote values, adding any that are not present locally
|
||||
for _, l := range item.GetRemoteList() {
|
||||
orderedKeys.UpsertRemote(l)
|
||||
}
|
||||
// Mixin recorded values, adding any that are not present locally
|
||||
// or remotely
|
||||
for _, l := range item.GetRecordedList() {
|
||||
orderedKeys.UpsertRecorded(l)
|
||||
}
|
||||
|
||||
for i, l := range orderedKeys.Items {
|
||||
var s proto.Schema
|
||||
if item.Array != nil && item.Array.SubType != nil {
|
||||
s = item.Array.SubType
|
||||
}
|
||||
|
||||
subitem, err := v.getItem(s, fmt.Sprintf("%d", i), l.RawElementData)
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Convert the Item to an Element
|
||||
newelem, err := subitem.CreateElement(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Append the element to the list
|
||||
result.Values = append(result.Values, newelem)
|
||||
}
|
||||
|
||||
return result, nil
|
||||
}
|
||||
|
||||
// doMapList merges 3 lists of maps together by collating their values.
|
||||
// tries to retain ordering
|
||||
func (v ElementBuildingVisitor) doMapList(meta apply.FieldMetaImpl, item *listItem) (*apply.ListElement, error) {
|
||||
key := meta.GetFieldMergeKeys()
|
||||
result := &apply.ListElement{
|
||||
FieldMetaImpl: apply.FieldMetaImpl{
|
||||
MergeType: apply.MergeStrategy,
|
||||
MergeKeys: key,
|
||||
Name: item.Name,
|
||||
},
|
||||
ListElementData: item.ListElementData,
|
||||
Values: []apply.Element{},
|
||||
}
|
||||
|
||||
// Use locally defined order, then add remote, then add recorded.
|
||||
orderedKeys := &apply.CombinedMapSlice{}
|
||||
|
||||
// Locally defined items come first and retain their order
|
||||
// as defined locally
|
||||
for _, l := range item.GetLocalList() {
|
||||
orderedKeys.UpsertLocal(key, l)
|
||||
}
|
||||
// Mixin remote values, adding any that are not present locally
|
||||
for _, l := range item.GetRemoteList() {
|
||||
orderedKeys.UpsertRemote(key, l)
|
||||
}
|
||||
// Mixin recorded values, adding any that are not present locally
|
||||
// or remotely
|
||||
for _, l := range item.GetRecordedList() {
|
||||
orderedKeys.UpsertRecorded(key, l)
|
||||
}
|
||||
|
||||
for i, l := range orderedKeys.Items {
|
||||
var s proto.Schema
|
||||
if item.Array != nil && item.Array.SubType != nil {
|
||||
s = item.Array.SubType
|
||||
}
|
||||
subitem, err := v.getItem(s, fmt.Sprintf("%d", i), l.RawElementData)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Build the element fully
|
||||
newelem, err := subitem.CreateElement(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Append the element to the list
|
||||
result.Values = append(result.Values, newelem)
|
||||
}
|
||||
|
||||
return result, nil
|
||||
}
|
||||
|
||||
// replaceListElement builds a new ListElement from a listItem
|
||||
// Uses the "replace" strategy and identify "same" elements across lists by their index
|
||||
func (v ElementBuildingVisitor) replaceListElement(meta apply.FieldMetaImpl, item *listItem) (*apply.ListElement, error) {
|
||||
meta.Name = item.Name
|
||||
result := &apply.ListElement{
|
||||
FieldMetaImpl: meta,
|
||||
ListElementData: item.ListElementData,
|
||||
Values: []apply.Element{},
|
||||
}
|
||||
|
||||
// Use the max length to iterate over the slices
|
||||
for i := 0; i < max(len(item.GetRecordedList()), len(item.GetLocalList()), len(item.GetRemoteList())); i++ {
|
||||
|
||||
// Lookup the item from each list
|
||||
data := apply.RawElementData{}
|
||||
if recorded, recordedSet := boundsSafeLookup(i, item.GetRecordedList()); recordedSet {
|
||||
data.SetRecorded(recorded)
|
||||
}
|
||||
if local, localSet := boundsSafeLookup(i, item.GetLocalList()); localSet {
|
||||
data.SetLocal(local)
|
||||
}
|
||||
if remote, remoteSet := boundsSafeLookup(i, item.GetRemoteList()); remoteSet {
|
||||
data.SetRemote(remote)
|
||||
}
|
||||
|
||||
// Create the Item
|
||||
var s proto.Schema
|
||||
if item.Array != nil && item.Array.SubType != nil {
|
||||
s = item.Array.SubType
|
||||
}
|
||||
subitem, err := v.getItem(s, fmt.Sprintf("%d", i), data)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Build the element
|
||||
newelem, err := subitem.CreateElement(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Append the element to the list
|
||||
result.Values = append(result.Values, newelem)
|
||||
}
|
||||
|
||||
return result, nil
|
||||
}
|
89
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/map_element.go
generated
vendored
Normal file
89
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/map_element.go
generated
vendored
Normal file
@ -0,0 +1,89 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
)
|
||||
|
||||
// mapElement builds a new mapElement from a mapItem
|
||||
func (v ElementBuildingVisitor) mapElement(meta apply.FieldMetaImpl, item *mapItem) (*apply.MapElement, error) {
|
||||
// Function to return schema type of the map values
|
||||
var fn schemaFn = func(string) proto.Schema {
|
||||
// All map values share the same schema
|
||||
if item.Map != nil && item.Map.SubType != nil {
|
||||
return item.Map.SubType
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Collect same fields from multiple maps into a map of elements
|
||||
values, err := v.createMapValues(fn, meta, item.MapElementData)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Return the result
|
||||
return &apply.MapElement{
|
||||
FieldMetaImpl: meta,
|
||||
MapElementData: item.MapElementData,
|
||||
Values: values,
|
||||
}, nil
|
||||
}
|
||||
|
||||
// schemaFn returns the schema for a field or map value based on its name or key
|
||||
type schemaFn func(key string) proto.Schema
|
||||
|
||||
// createMapValues combines the recorded, local and remote values from
|
||||
// data into a map of elements.
|
||||
func (v ElementBuildingVisitor) createMapValues(
|
||||
schemaFn schemaFn,
|
||||
meta apply.FieldMetaImpl,
|
||||
data apply.MapElementData) (map[string]apply.Element, error) {
|
||||
|
||||
// Collate each key in the map
|
||||
values := map[string]apply.Element{}
|
||||
for _, key := range keysUnion(data.GetRecordedMap(), data.GetLocalMap(), data.GetRemoteMap()) {
|
||||
combined := apply.RawElementData{}
|
||||
if recorded, recordedSet := nilSafeLookup(key, data.GetRecordedMap()); recordedSet {
|
||||
combined.SetRecorded(recorded)
|
||||
}
|
||||
if local, localSet := nilSafeLookup(key, data.GetLocalMap()); localSet {
|
||||
combined.SetLocal(local)
|
||||
}
|
||||
if remote, remoteSet := nilSafeLookup(key, data.GetRemoteMap()); remoteSet {
|
||||
combined.SetRemote(remote)
|
||||
}
|
||||
|
||||
// Create an item for the field
|
||||
field, err := v.getItem(schemaFn(key), key, combined)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Build the element for this field
|
||||
element, err := field.CreateElement(v)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Add the field element to the map
|
||||
values[key] = element
|
||||
}
|
||||
return values, nil
|
||||
}
|
227
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/openapi.go
generated
vendored
Normal file
227
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/openapi.go
generated
vendored
Normal file
@ -0,0 +1,227 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
)
|
||||
|
||||
// Contains functions for casting openapi interfaces to their underlying types
|
||||
|
||||
// getSchemaType returns the string type of the schema - e.g. array, primitive, map, kind, reference
|
||||
func getSchemaType(schema proto.Schema) string {
|
||||
if schema == nil {
|
||||
return ""
|
||||
}
|
||||
visitor := &baseSchemaVisitor{}
|
||||
schema.Accept(visitor)
|
||||
return visitor.Kind
|
||||
}
|
||||
|
||||
// getKind converts schema to an *proto.Kind object
|
||||
func getKind(schema proto.Schema) (*proto.Kind, error) {
|
||||
if schema == nil {
|
||||
return nil, nil
|
||||
}
|
||||
visitor := &kindSchemaVisitor{}
|
||||
schema.Accept(visitor)
|
||||
return visitor.Result, visitor.Err
|
||||
}
|
||||
|
||||
// getArray converts schema to an *proto.Array object
|
||||
func getArray(schema proto.Schema) (*proto.Array, error) {
|
||||
if schema == nil {
|
||||
return nil, nil
|
||||
}
|
||||
visitor := &arraySchemaVisitor{}
|
||||
schema.Accept(visitor)
|
||||
return visitor.Result, visitor.Err
|
||||
}
|
||||
|
||||
// getMap converts schema to an *proto.Map object
|
||||
func getMap(schema proto.Schema) (*proto.Map, error) {
|
||||
if schema == nil {
|
||||
return nil, nil
|
||||
}
|
||||
visitor := &mapSchemaVisitor{}
|
||||
schema.Accept(visitor)
|
||||
return visitor.Result, visitor.Err
|
||||
}
|
||||
|
||||
// getPrimitive converts schema to an *proto.Primitive object
|
||||
func getPrimitive(schema proto.Schema) (*proto.Primitive, error) {
|
||||
if schema == nil {
|
||||
return nil, nil
|
||||
}
|
||||
visitor := &primitiveSchemaVisitor{}
|
||||
schema.Accept(visitor)
|
||||
return visitor.Result, visitor.Err
|
||||
}
|
||||
|
||||
type baseSchemaVisitor struct {
|
||||
Err error
|
||||
Kind string
|
||||
}
|
||||
|
||||
// VisitArray implements openapi
|
||||
func (v *baseSchemaVisitor) VisitArray(array *proto.Array) {
|
||||
v.Kind = "array"
|
||||
v.Err = fmt.Errorf("Array type not expected")
|
||||
}
|
||||
|
||||
// MergeMap implements openapi
|
||||
func (v *baseSchemaVisitor) VisitMap(*proto.Map) {
|
||||
v.Kind = "map"
|
||||
v.Err = fmt.Errorf("Map type not expected")
|
||||
}
|
||||
|
||||
// MergePrimitive implements openapi
|
||||
func (v *baseSchemaVisitor) VisitPrimitive(*proto.Primitive) {
|
||||
v.Kind = "primitive"
|
||||
v.Err = fmt.Errorf("Primitive type not expected")
|
||||
}
|
||||
|
||||
// VisitKind implements openapi
|
||||
func (v *baseSchemaVisitor) VisitKind(*proto.Kind) {
|
||||
v.Kind = "kind"
|
||||
v.Err = fmt.Errorf("Kind type not expected")
|
||||
}
|
||||
|
||||
// VisitReference implements openapi
|
||||
func (v *baseSchemaVisitor) VisitReference(reference proto.Reference) {
|
||||
v.Kind = "reference"
|
||||
v.Err = fmt.Errorf("Reference type not expected")
|
||||
}
|
||||
|
||||
type kindSchemaVisitor struct {
|
||||
baseSchemaVisitor
|
||||
Result *proto.Kind
|
||||
}
|
||||
|
||||
// VisitKind implements openapi
|
||||
func (v *kindSchemaVisitor) VisitKind(result *proto.Kind) {
|
||||
v.Result = result
|
||||
v.Kind = "kind"
|
||||
}
|
||||
|
||||
// VisitReference implements openapi
|
||||
func (v *kindSchemaVisitor) VisitReference(reference proto.Reference) {
|
||||
reference.SubSchema().Accept(v)
|
||||
if v.Err == nil {
|
||||
v.Err = copyExtensions(reference.GetPath().String(), reference.GetExtensions(), v.Result.Extensions)
|
||||
}
|
||||
}
|
||||
|
||||
func copyExtensions(field string, from, to map[string]interface{}) error {
|
||||
// Copy extensions from field to type for references
|
||||
for key, val := range from {
|
||||
if curr, found := to[key]; found {
|
||||
// Don't allow the same extension to be defined both on the field and on the type
|
||||
return fmt.Errorf("Cannot override value for extension %s on field %s from %v to %v",
|
||||
key, field, curr, val)
|
||||
}
|
||||
to[key] = val
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type mapSchemaVisitor struct {
|
||||
baseSchemaVisitor
|
||||
Result *proto.Map
|
||||
}
|
||||
|
||||
// MergeMap implements openapi
|
||||
func (v *mapSchemaVisitor) VisitMap(result *proto.Map) {
|
||||
v.Result = result
|
||||
v.Kind = "map"
|
||||
}
|
||||
|
||||
// VisitReference implements openapi
|
||||
func (v *mapSchemaVisitor) VisitReference(reference proto.Reference) {
|
||||
reference.SubSchema().Accept(v)
|
||||
if v.Err == nil {
|
||||
v.Err = copyExtensions(reference.GetPath().String(), reference.GetExtensions(), v.Result.Extensions)
|
||||
}
|
||||
}
|
||||
|
||||
type arraySchemaVisitor struct {
|
||||
baseSchemaVisitor
|
||||
Result *proto.Array
|
||||
}
|
||||
|
||||
// VisitArray implements openapi
|
||||
func (v *arraySchemaVisitor) VisitArray(result *proto.Array) {
|
||||
v.Result = result
|
||||
v.Kind = "array"
|
||||
v.Err = copySubElementPatchStrategy(result.Path.String(), result.GetExtensions(), result.SubType.GetExtensions())
|
||||
}
|
||||
|
||||
// copyPatchStrategy copies the strategies to subelements to the subtype
|
||||
// e.g. PodTemplate.Volumes is a []Volume with "x-kubernetes-patch-strategy": "merge,retainKeys"
|
||||
// the "retainKeys" strategy applies to merging Volumes, and must be copied to the sub element
|
||||
func copySubElementPatchStrategy(field string, from, to map[string]interface{}) error {
|
||||
// Check if the parent has a patch strategy extension
|
||||
if ext, found := from["x-kubernetes-patch-strategy"]; found {
|
||||
strategy, ok := ext.(string)
|
||||
if !ok {
|
||||
return fmt.Errorf("Expected string value for x-kubernetes-patch-strategy on %s, was %T",
|
||||
field, ext)
|
||||
}
|
||||
// Check of the parent patch strategy has a sub patch strategy, and if so copy to the sub type
|
||||
if strings.Contains(strategy, ",") {
|
||||
strategies := strings.Split(strategy, ",")
|
||||
if len(strategies) != 2 {
|
||||
// Only 1 sub strategy is supported
|
||||
return fmt.Errorf(
|
||||
"Expected between 0 and 2 elements for x-kubernetes-patch-merge-strategy by got %v",
|
||||
strategies)
|
||||
}
|
||||
to["x-kubernetes-patch-strategy"] = strategies[1]
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// MergePrimitive implements openapi
|
||||
func (v *arraySchemaVisitor) VisitReference(reference proto.Reference) {
|
||||
reference.SubSchema().Accept(v)
|
||||
if v.Err == nil {
|
||||
v.Err = copyExtensions(reference.GetPath().String(), reference.GetExtensions(), v.Result.Extensions)
|
||||
}
|
||||
}
|
||||
|
||||
type primitiveSchemaVisitor struct {
|
||||
baseSchemaVisitor
|
||||
Result *proto.Primitive
|
||||
}
|
||||
|
||||
// MergePrimitive implements openapi
|
||||
func (v *primitiveSchemaVisitor) VisitPrimitive(result *proto.Primitive) {
|
||||
v.Result = result
|
||||
v.Kind = "primitive"
|
||||
}
|
||||
|
||||
// VisitReference implements openapi
|
||||
func (v *primitiveSchemaVisitor) VisitReference(reference proto.Reference) {
|
||||
reference.SubSchema().Accept(v)
|
||||
if v.Err == nil {
|
||||
v.Err = copyExtensions(reference.GetPath().String(), reference.GetExtensions(), v.Result.Extensions)
|
||||
}
|
||||
}
|
28
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/primitive_element.go
generated
vendored
Normal file
28
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/primitive_element.go
generated
vendored
Normal file
@ -0,0 +1,28 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import "k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
|
||||
// primitiveElement builds a new primitiveElement from a PrimitiveItem
|
||||
func (v ElementBuildingVisitor) primitiveElement(item *primitiveItem) (*apply.PrimitiveElement, error) {
|
||||
meta := apply.FieldMetaImpl{Name: item.Name}
|
||||
return &apply.PrimitiveElement{
|
||||
FieldMetaImpl: meta,
|
||||
RawElementData: item.RawElementData,
|
||||
}, nil
|
||||
}
|
49
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/suite_test.go
generated
vendored
Normal file
49
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/suite_test.go
generated
vendored
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
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 parse_test
|
||||
|
||||
import (
|
||||
. "github.com/onsi/ginkgo"
|
||||
. "github.com/onsi/ginkgo/config"
|
||||
. "github.com/onsi/ginkgo/types"
|
||||
. "github.com/onsi/gomega"
|
||||
|
||||
"fmt"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestOpenapi(t *testing.T) {
|
||||
RegisterFailHandler(Fail)
|
||||
RunSpecsWithDefaultAndCustomReporters(t, "Openapi Suite", []Reporter{newlineReporter{}})
|
||||
}
|
||||
|
||||
// Print a newline after the default newlineReporter due to issue
|
||||
// https://github.com/jstemmer/go-junit-report/issues/31
|
||||
type newlineReporter struct{}
|
||||
|
||||
func (newlineReporter) SpecSuiteWillBegin(config GinkgoConfigType, summary *SuiteSummary) {}
|
||||
|
||||
func (newlineReporter) BeforeSuiteDidRun(setupSummary *SetupSummary) {}
|
||||
|
||||
func (newlineReporter) AfterSuiteDidRun(setupSummary *SetupSummary) {}
|
||||
|
||||
func (newlineReporter) SpecWillRun(specSummary *SpecSummary) {}
|
||||
|
||||
func (newlineReporter) SpecDidComplete(specSummary *SpecSummary) {}
|
||||
|
||||
// SpecSuiteDidEnd Prints a newline between "35 Passed | 0 Failed | 0 Pending | 0 Skipped" and "--- PASS:"
|
||||
func (newlineReporter) SpecSuiteDidEnd(summary *SuiteSummary) { fmt.Printf("\n") }
|
46
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/type_element.go
generated
vendored
Normal file
46
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/type_element.go
generated
vendored
Normal file
@ -0,0 +1,46 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
)
|
||||
|
||||
// typeElement builds a new mapElement from a typeItem
|
||||
func (v ElementBuildingVisitor) typeElement(meta apply.FieldMetaImpl, item *typeItem) (*apply.TypeElement, error) {
|
||||
// Function to get the schema of a field from its key
|
||||
var fn schemaFn = func(key string) proto.Schema {
|
||||
if item.Type != nil && item.Type.Fields != nil {
|
||||
return item.Type.Fields[key]
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Collect same fields from multiple maps into a map of elements
|
||||
values, err := v.createMapValues(fn, meta, item.MapElementData)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Return the result
|
||||
return &apply.TypeElement{
|
||||
FieldMetaImpl: meta,
|
||||
MapElementData: item.MapElementData,
|
||||
Values: values,
|
||||
}, nil
|
||||
}
|
181
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/util.go
generated
vendored
Normal file
181
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/util.go
generated
vendored
Normal file
@ -0,0 +1,181 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"strings"
|
||||
|
||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
||||
"k8s.io/kube-openapi/pkg/util/proto"
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
)
|
||||
|
||||
// nilSafeLookup returns the value from the map if the map is non-nil
|
||||
func nilSafeLookup(key string, from map[string]interface{}) (interface{}, bool) {
|
||||
if from != nil {
|
||||
value, found := from[key]
|
||||
return value, found
|
||||
}
|
||||
// Not present
|
||||
return nil, false
|
||||
}
|
||||
|
||||
// boundsSafeLookup returns the value from the slice if the slice is non-nil and
|
||||
// the index is in bounds.
|
||||
func boundsSafeLookup(index int, from []interface{}) (interface{}, bool) {
|
||||
if from != nil && len(from) > index {
|
||||
return from[index], true
|
||||
}
|
||||
return nil, false
|
||||
}
|
||||
|
||||
// keysUnion returns a slice containing the union of the keys present in the arguments
|
||||
func keysUnion(maps ...map[string]interface{}) []string {
|
||||
keys := map[string]interface{}{}
|
||||
for _, m := range maps {
|
||||
for k := range m {
|
||||
keys[k] = nil
|
||||
}
|
||||
}
|
||||
result := []string{}
|
||||
for key := range keys {
|
||||
result = append(result, key)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
// max returns the argument with the highest value
|
||||
func max(values ...int) int {
|
||||
v := 0
|
||||
for _, i := range values {
|
||||
if i > v {
|
||||
v = i
|
||||
}
|
||||
}
|
||||
return v
|
||||
}
|
||||
|
||||
// getType returns the type of the arguments. If the arguments don't have matching
|
||||
// types, getType returns an error. Nil types matching everything.
|
||||
func getType(args ...interface{}) (reflect.Type, error) {
|
||||
var last interface{}
|
||||
for _, next := range args {
|
||||
// Skip nil values
|
||||
if next == nil {
|
||||
continue
|
||||
}
|
||||
|
||||
// Set the first non-nil value we find and continue
|
||||
if last == nil {
|
||||
last = next
|
||||
continue
|
||||
}
|
||||
|
||||
// Verify the types of the values match
|
||||
if reflect.TypeOf(last).Kind() != reflect.TypeOf(next).Kind() {
|
||||
return nil, fmt.Errorf("missmatching non-nil types for the same field: %T %T", last, next)
|
||||
}
|
||||
}
|
||||
|
||||
return reflect.TypeOf(last), nil
|
||||
}
|
||||
|
||||
// getFieldMeta parses the metadata about the field from the openapi spec
|
||||
func getFieldMeta(s proto.Schema, name string) (apply.FieldMetaImpl, error) {
|
||||
m := apply.FieldMetaImpl{}
|
||||
if s != nil {
|
||||
ext := s.GetExtensions()
|
||||
if e, found := ext["x-kubernetes-patch-strategy"]; found {
|
||||
strategy, ok := e.(string)
|
||||
if !ok {
|
||||
return apply.FieldMetaImpl{}, fmt.Errorf("Expected string for x-kubernetes-patch-strategy by got %T", s)
|
||||
}
|
||||
|
||||
// Take the first strategy if there are substrategies.
|
||||
// Sub strategies are copied to sub types in openapi.go
|
||||
strategies := strings.Split(strategy, ",")
|
||||
if len(strategies) > 2 {
|
||||
return apply.FieldMetaImpl{}, fmt.Errorf("Expected between 0 and 2 elements for x-kubernetes-patch-merge-strategy by got %v", strategies)
|
||||
}
|
||||
// For lists, choose the strategy for this type, not the subtype
|
||||
m.MergeType = strategies[0]
|
||||
}
|
||||
if k, found := ext["x-kubernetes-patch-merge-key"]; found {
|
||||
key, ok := k.(string)
|
||||
if !ok {
|
||||
return apply.FieldMetaImpl{}, fmt.Errorf("Expected string for x-kubernetes-patch-merge-key by got %T", k)
|
||||
}
|
||||
m.MergeKeys = apply.MergeKeys(strings.Split(key, ","))
|
||||
}
|
||||
}
|
||||
m.Name = name
|
||||
return m, nil
|
||||
}
|
||||
|
||||
// getCommonGroupVersionKind verifies that the recorded, local and remote all share
|
||||
// the same GroupVersionKind and returns the value
|
||||
func getCommonGroupVersionKind(recorded, local, remote map[string]interface{}) (schema.GroupVersionKind, error) {
|
||||
recordedGVK, err := getGroupVersionKind(recorded)
|
||||
if err != nil {
|
||||
return schema.GroupVersionKind{}, err
|
||||
}
|
||||
localGVK, err := getGroupVersionKind(local)
|
||||
if err != nil {
|
||||
return schema.GroupVersionKind{}, err
|
||||
}
|
||||
remoteGVK, err := getGroupVersionKind(remote)
|
||||
if err != nil {
|
||||
return schema.GroupVersionKind{}, err
|
||||
}
|
||||
|
||||
if !reflect.DeepEqual(recordedGVK, localGVK) || !reflect.DeepEqual(localGVK, remoteGVK) {
|
||||
return schema.GroupVersionKind{},
|
||||
fmt.Errorf("group version kinds do not match (recorded: %v local: %v remote: %v)",
|
||||
recordedGVK, localGVK, remoteGVK)
|
||||
}
|
||||
return recordedGVK, nil
|
||||
}
|
||||
|
||||
// getGroupVersionKind returns the GroupVersionKind of the object
|
||||
func getGroupVersionKind(config map[string]interface{}) (schema.GroupVersionKind, error) {
|
||||
gvk := schema.GroupVersionKind{}
|
||||
if gv, found := config["apiVersion"]; found {
|
||||
casted, ok := gv.(string)
|
||||
if !ok {
|
||||
return gvk, fmt.Errorf("Expected string for apiVersion, found %T", gv)
|
||||
}
|
||||
s := strings.Split(casted, "/")
|
||||
if len(s) != 1 {
|
||||
gvk.Group = s[0]
|
||||
}
|
||||
gvk.Version = s[len(s)-1]
|
||||
} else {
|
||||
return gvk, fmt.Errorf("Missing apiVersion in Kind %v", config)
|
||||
}
|
||||
if k, found := config["kind"]; found {
|
||||
casted, ok := k.(string)
|
||||
if !ok {
|
||||
return gvk, fmt.Errorf("Expected string for kind, found %T", k)
|
||||
}
|
||||
gvk.Kind = casted
|
||||
} else {
|
||||
return gvk, fmt.Errorf("Missing kind in Kind %v", config)
|
||||
}
|
||||
return gvk, nil
|
||||
}
|
79
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/visitor.go
generated
vendored
Normal file
79
vendor/k8s.io/kubernetes/pkg/kubectl/apply/parse/visitor.go
generated
vendored
Normal file
@ -0,0 +1,79 @@
|
||||
/*
|
||||
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 parse
|
||||
|
||||
import (
|
||||
"k8s.io/kubernetes/pkg/kubectl/apply"
|
||||
"k8s.io/kubernetes/pkg/kubectl/cmd/util/openapi"
|
||||
)
|
||||
|
||||
// ItemVisitor provides an interface for Items to Accept and call
|
||||
// the Visit function that corresponds to its actual type.
|
||||
type ItemVisitor interface {
|
||||
// CreatePrimitiveElement builds an Element for a primitiveItem
|
||||
CreatePrimitiveElement(*primitiveItem) (apply.Element, error)
|
||||
|
||||
// CreateListElement builds an Element for a listItem
|
||||
CreateListElement(*listItem) (apply.Element, error)
|
||||
|
||||
// CreateMapElement builds an Element for a mapItem
|
||||
CreateMapElement(*mapItem) (apply.Element, error)
|
||||
|
||||
// CreateTypeElement builds an Element for a typeItem
|
||||
CreateTypeElement(*typeItem) (apply.Element, error)
|
||||
}
|
||||
|
||||
// ElementBuildingVisitor creates an Elements from Items
|
||||
// An Element combines the values from the Item with the field metadata.
|
||||
type ElementBuildingVisitor struct {
|
||||
resources openapi.Resources
|
||||
}
|
||||
|
||||
// CreatePrimitiveElement creates a primitiveElement
|
||||
func (v ElementBuildingVisitor) CreatePrimitiveElement(item *primitiveItem) (apply.Element, error) {
|
||||
return v.primitiveElement(item)
|
||||
}
|
||||
|
||||
// CreateListElement creates a ListElement
|
||||
func (v ElementBuildingVisitor) CreateListElement(item *listItem) (apply.Element, error) {
|
||||
meta, err := getFieldMeta(item.GetMeta(), item.Name)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if meta.GetFieldMergeType() == apply.MergeStrategy {
|
||||
return v.mergeListElement(meta, item)
|
||||
}
|
||||
return v.replaceListElement(meta, item)
|
||||
}
|
||||
|
||||
// CreateMapElement creates a mapElement
|
||||
func (v ElementBuildingVisitor) CreateMapElement(item *mapItem) (apply.Element, error) {
|
||||
meta, err := getFieldMeta(item.GetMeta(), item.Name)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return v.mapElement(meta, item)
|
||||
}
|
||||
|
||||
// CreateTypeElement creates a typeElement
|
||||
func (v ElementBuildingVisitor) CreateTypeElement(item *typeItem) (apply.Element, error) {
|
||||
meta, err := getFieldMeta(item.GetMeta(), item.Name)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return v.typeElement(meta, item)
|
||||
}
|
Reference in New Issue
Block a user