mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-08-09 12:07:47 +00:00
Introduce ObjectConvertor for conversion to known API versions
Will allow clients to transform internal objects to a version suitable for external output.
This commit is contained in:
parent
2d54dfe249
commit
778a50d00b
@ -211,6 +211,46 @@ func (s *Scheme) Convert(in, out interface{}) error {
|
|||||||
return s.converter.Convert(in, out, 0, s.generateConvertMeta(inVersion, outVersion))
|
return s.converter.Convert(in, out, 0, s.generateConvertMeta(inVersion, outVersion))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ConvertToVersion attempts to convert an input object to its matching Kind in another
|
||||||
|
// version within this scheme. Will return an error if the provided version does not
|
||||||
|
// contain the inKind (or a mapping by name defined with AddKnownTypeWithName).
|
||||||
|
func (s *Scheme) ConvertToVersion(in interface{}, outVersion string) (interface{}, error) {
|
||||||
|
t := reflect.TypeOf(in)
|
||||||
|
if t.Kind() != reflect.Ptr {
|
||||||
|
return nil, fmt.Errorf("only pointer types may be converted: %v", t)
|
||||||
|
}
|
||||||
|
t = t.Elem()
|
||||||
|
if t.Kind() != reflect.Struct {
|
||||||
|
return nil, fmt.Errorf("only pointers to struct types may be converted: %v", t)
|
||||||
|
}
|
||||||
|
|
||||||
|
kinds, ok := s.typeToKind[t]
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("%v cannot be converted into version %q", t, outVersion)
|
||||||
|
}
|
||||||
|
outKind := kinds[0]
|
||||||
|
|
||||||
|
inVersion, _, err := s.ObjectVersionAndKind(in)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
out, err := s.NewObject(outVersion, outKind)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := s.converter.Convert(in, out, 0, s.generateConvertMeta(inVersion, outVersion)); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := s.SetVersionAndKind(outVersion, outKind, out); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return out, nil
|
||||||
|
}
|
||||||
|
|
||||||
// generateConvertMeta constructs the meta value we pass to Convert.
|
// generateConvertMeta constructs the meta value we pass to Convert.
|
||||||
func (s *Scheme) generateConvertMeta(srcVersion, destVersion string) *Meta {
|
func (s *Scheme) generateConvertMeta(srcVersion, destVersion string) *Meta {
|
||||||
return &Meta{
|
return &Meta{
|
||||||
|
@ -240,6 +240,45 @@ func TestMultipleNames(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestKnownTypes(t *testing.T) {
|
||||||
|
s := GetTestScheme()
|
||||||
|
if len(s.KnownTypes("v2")) != 0 {
|
||||||
|
t.Errorf("should have no known types for v2")
|
||||||
|
}
|
||||||
|
|
||||||
|
types := s.KnownTypes("v1")
|
||||||
|
for _, s := range []string{"TestType1", "TestType2", "TestType3", "ExternalInternalSame"} {
|
||||||
|
if _, ok := types[s]; !ok {
|
||||||
|
t.Errorf("missing type %q", s)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestConvertToVersion(t *testing.T) {
|
||||||
|
s := GetTestScheme()
|
||||||
|
tt := &TestType1{A: "I'm not a pointer object"}
|
||||||
|
other, err := s.ConvertToVersion(tt, "v1")
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("Failure: %v", err)
|
||||||
|
}
|
||||||
|
converted, ok := other.(*ExternalTestType1)
|
||||||
|
if !ok {
|
||||||
|
t.Fatalf("Got wrong type")
|
||||||
|
}
|
||||||
|
if tt.A != converted.A {
|
||||||
|
t.Fatalf("Failed to convert object correctly: %#v", converted)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestConvertToVersionErr(t *testing.T) {
|
||||||
|
s := GetTestScheme()
|
||||||
|
tt := TestType1{A: "I'm not a pointer object"}
|
||||||
|
_, err := s.ConvertToVersion(tt, "v1")
|
||||||
|
if err == nil {
|
||||||
|
t.Fatalf("unexpected non-error")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func TestEncode_NonPtr(t *testing.T) {
|
func TestEncode_NonPtr(t *testing.T) {
|
||||||
s := GetTestScheme()
|
s := GetTestScheme()
|
||||||
tt := TestType1{A: "I'm not a pointer object"}
|
tt := TestType1{A: "I'm not a pointer object"}
|
||||||
|
@ -33,6 +33,11 @@ type Codec interface {
|
|||||||
Encoder
|
Encoder
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ObjectConvertor converts an object to a different version.
|
||||||
|
type ObjectConvertor interface {
|
||||||
|
ConvertToVersion(in Object, outVersion string) (out Object, err error)
|
||||||
|
}
|
||||||
|
|
||||||
// ObjectTyper contains methods for extracting the APIVersion and Kind
|
// ObjectTyper contains methods for extracting the APIVersion and Kind
|
||||||
// of objects.
|
// of objects.
|
||||||
type ObjectTyper interface {
|
type ObjectTyper interface {
|
||||||
|
@ -17,6 +17,7 @@ limitations under the License.
|
|||||||
package runtime
|
package runtime
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"fmt"
|
||||||
"reflect"
|
"reflect"
|
||||||
|
|
||||||
"github.com/GoogleCloudPlatform/kubernetes/pkg/conversion"
|
"github.com/GoogleCloudPlatform/kubernetes/pkg/conversion"
|
||||||
@ -223,6 +224,23 @@ func (s *Scheme) Convert(in, out interface{}) error {
|
|||||||
return s.raw.Convert(in, out)
|
return s.raw.Convert(in, out)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ConvertToVersion attempts to convert an input object to its matching Kind in another
|
||||||
|
// version within this scheme. Will return an error if the provided version does not
|
||||||
|
// contain the inKind (or a mapping by name defined with AddKnownTypeWithName). Will also
|
||||||
|
// return an error if the conversion does not result in a valid Object being
|
||||||
|
// returned.
|
||||||
|
func (s *Scheme) ConvertToVersion(in Object, outVersion string) (Object, error) {
|
||||||
|
unknown, err := s.raw.ConvertToVersion(in, outVersion)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
obj, ok := unknown.(Object)
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("the provided object cannot be converted to a runtime.Object: %#v", unknown)
|
||||||
|
}
|
||||||
|
return obj, nil
|
||||||
|
}
|
||||||
|
|
||||||
// EncodeToVersion turns the given api object into an appropriate JSON string.
|
// EncodeToVersion turns the given api object into an appropriate JSON string.
|
||||||
// Will return an error if the object doesn't have an embedded TypeMeta.
|
// Will return an error if the object doesn't have an embedded TypeMeta.
|
||||||
// Obj may be a pointer to a struct, or a struct. If a struct, a copy
|
// Obj may be a pointer to a struct, or a struct. If a struct, a copy
|
||||||
|
Loading…
Reference in New Issue
Block a user