Use meta.Interface and meta.Accessor

pull/6/head
Clayton Coleman 2014-10-23 18:01:25 -04:00
parent e5c924585c
commit 3df1c2f29d
7 changed files with 68 additions and 68 deletions

View File

@ -373,11 +373,11 @@ func executeAPIRequest(ctx api.Context, method string, c *client.Client) bool {
if err != nil {
glog.Fatalf("error obtaining resource version for update: %v", err)
}
jsonBase, err := meta.FindAccessor(obj)
meta, err := meta.Accessor(obj)
if err != nil {
glog.Fatalf("error finding json base for update: %v", err)
}
version = jsonBase.ResourceVersion()
version = meta.ResourceVersion()
verb = "PUT"
setBody = true
if !validStorage || !hasSuffix {
@ -409,7 +409,7 @@ func executeAPIRequest(ctx api.Context, method string, c *client.Client) bool {
if err != nil {
glog.Fatalf("error setting resource version: %v", err)
}
jsonBase, err := meta.FindAccessor(obj)
jsonBase, err := meta.Accessor(obj)
if err != nil {
glog.Fatalf("error setting resource version: %v", err)
}

View File

@ -24,46 +24,63 @@ import (
"github.com/GoogleCloudPlatform/kubernetes/pkg/runtime"
)
// FindAccessor takes an arbitary type and returns an Accessor interfaces.
// obj must be a pointer to an api type. An error is returned if the minimum
// required fields are missing.
func FindAccessor(obj interface{}) (Accessor, error) {
// Interface lets you work with object metadata from any of the versioned or
// internal API objects.
type Interface interface {
Name() string
SetName(name string)
UID() string
SetUID(uid string)
APIVersion() string
SetAPIVersion(version string)
Kind() string
SetKind(kind string)
ResourceVersion() string
SetResourceVersion(version string)
SelfLink() string
SetSelfLink(selfLink string)
}
// Accessor takes an arbitary object pointer and returns meta.Interface.
// obj must be a pointer to an API type. An error is returned if the minimum
// required fields are missing. Fields that are not required return the default
// value and are a no-op if set.
func Accessor(obj interface{}) (Interface, error) {
v, err := conversion.EnforcePtr(obj)
if err != nil {
return nil, err
}
t := v.Type()
name := t.Name()
if v.Kind() != reflect.Struct {
return nil, fmt.Errorf("expected struct, but got %v: %v (%#v)", v.Kind(), name, v.Interface())
return nil, fmt.Errorf("expected struct, but got %v: %v (%#v)", v.Kind(), t, v.Interface())
}
typeMeta := v.FieldByName("TypeMeta")
if !typeMeta.IsValid() {
return nil, fmt.Errorf("struct %v lacks embedded TypeMeta type", name)
return nil, fmt.Errorf("struct %v lacks embedded TypeMeta type", t)
}
a := &genericAccessor{}
if err := findTypeMeta(typeMeta, a); err != nil {
if err := extractFromTypeMeta(typeMeta, a); err != nil {
return nil, fmt.Errorf("unable to find type fields on %#v", typeMeta)
}
objectMeta := v.FieldByName("ObjectMeta")
if objectMeta.IsValid() {
// look for the ObjectMeta fields
if err := findObjectMeta(objectMeta, a); err != nil {
if err := extractFromObjectMeta(objectMeta, a); err != nil {
return nil, fmt.Errorf("unable to find object fields on %#v", objectMeta)
}
} else {
listMeta := v.FieldByName("ListMeta")
if listMeta.IsValid() {
// look for the ListMeta fields
if err := findListMeta(listMeta, a); err != nil {
if err := extractFromListMeta(listMeta, a); err != nil {
return nil, fmt.Errorf("unable to find list fields on %#v", listMeta)
}
} else {
// look for the older TypeMeta with all metadata
if err := findObjectMeta(typeMeta, a); err != nil {
if err := extractFromObjectMeta(typeMeta, a); err != nil {
return nil, fmt.Errorf("unable to find object fields on %#v", typeMeta)
}
}
@ -82,7 +99,7 @@ func NewResourceVersioner() runtime.ResourceVersioner {
type resourceAccessor struct{}
func (v resourceAccessor) ResourceVersion(obj runtime.Object) (string, error) {
accessor, err := FindAccessor(obj)
accessor, err := Accessor(obj)
if err != nil {
return "", err
}
@ -90,7 +107,7 @@ func (v resourceAccessor) ResourceVersion(obj runtime.Object) (string, error) {
}
func (v resourceAccessor) SetResourceVersion(obj runtime.Object, version string) error {
accessor, err := FindAccessor(obj)
accessor, err := Accessor(obj)
if err != nil {
return err
}
@ -99,7 +116,7 @@ func (v resourceAccessor) SetResourceVersion(obj runtime.Object, version string)
}
func (v resourceAccessor) Name(obj runtime.Object) (string, error) {
accessor, err := FindAccessor(obj)
accessor, err := Accessor(obj)
if err != nil {
return "", err
}
@ -107,7 +124,7 @@ func (v resourceAccessor) Name(obj runtime.Object) (string, error) {
}
func (v resourceAccessor) SelfLink(obj runtime.Object) (string, error) {
accessor, err := FindAccessor(obj)
accessor, err := Accessor(obj)
if err != nil {
return "", err
}
@ -115,7 +132,7 @@ func (v resourceAccessor) SelfLink(obj runtime.Object) (string, error) {
}
func (v resourceAccessor) SetSelfLink(obj runtime.Object, selfLink string) error {
accessor, err := FindAccessor(obj)
accessor, err := Accessor(obj)
if err != nil {
return err
}
@ -128,23 +145,6 @@ func NewSelfLinker() runtime.SelfLinker {
return resourceAccessor{}
}
// Accessor lets you work with object metadata from any of the versioned or
// internal APIruntime.Objects.
type Accessor interface {
Name() string
SetName(name string)
UID() string
SetUID(uid string)
APIVersion() string
SetAPIVersion(version string)
Kind() string
SetKind(kind string)
ResourceVersion() string
SetResourceVersion(version string)
SelfLink() string
SetSelfLink(selfLink string)
}
// genericAccessor contains pointers to strings that can modify an arbitrary
// struct and implements the Accessor interface.
type genericAccessor struct {
@ -241,8 +241,8 @@ func fieldPtr(v reflect.Value, fieldName string, dest interface{}) error {
return fmt.Errorf("Couldn't assign/convert %v to %v", field.Type(), v.Type())
}
// findTypeMeta extracts pointers to version and kind fields from an object
func findTypeMeta(v reflect.Value, a *genericAccessor) error {
// extractFromTypeMeta extracts pointers to version and kind fields from an object
func extractFromTypeMeta(v reflect.Value, a *genericAccessor) error {
if err := fieldPtr(v, "APIVersion", &a.apiVersion); err != nil {
return err
}
@ -252,8 +252,8 @@ func findTypeMeta(v reflect.Value, a *genericAccessor) error {
return nil
}
// findObjectMeta extracts pointers to metadata fields from an object
func findObjectMeta(v reflect.Value, a *genericAccessor) error {
// extractFromObjectMeta extracts pointers to metadata fields from an object
func extractFromObjectMeta(v reflect.Value, a *genericAccessor) error {
if err := fieldPtr(v, "Name", &a.name); err != nil {
return err
}
@ -269,8 +269,8 @@ func findObjectMeta(v reflect.Value, a *genericAccessor) error {
return nil
}
// findObjectMeta extracts pointers to metadata fields from a list object
func findListMeta(v reflect.Value, a *genericAccessor) error {
// extractFromObjectMeta extracts pointers to metadata fields from a list object
func extractFromListMeta(v reflect.Value, a *genericAccessor) error {
if err := fieldPtr(v, "ResourceVersion", &a.resourceVersion); err != nil {
return err
}

View File

@ -46,7 +46,7 @@ func TestGenericTypeMeta(t *testing.T) {
SelfLink: "some/place/only/we/know",
},
}
accessor, err := FindAccessor(&j)
accessor, err := Accessor(&j)
if err != nil {
t.Fatalf("new err: %v", err)
}
@ -125,7 +125,7 @@ func TestGenericObjectMeta(t *testing.T) {
SelfLink: "some/place/only/we/know",
},
}
accessor, err := FindAccessor(&j)
accessor, err := Accessor(&j)
if err != nil {
t.Fatalf("new err: %v", err)
}
@ -199,7 +199,7 @@ func TestGenericListMeta(t *testing.T) {
SelfLink: "some/place/only/we/know",
},
}
accessor, err := FindAccessor(&j)
accessor, err := Accessor(&j)
if err != nil {
t.Fatalf("new err: %v", err)
}

View File

@ -36,7 +36,7 @@ func GetReference(obj runtime.Object) (*ObjectReference, error) {
if obj == nil {
return nil, ErrNilObject
}
accessor, err := meta.FindAccessor(obj)
meta, err := meta.Accessor(obj)
if err != nil {
return nil, err
}
@ -44,16 +44,16 @@ func GetReference(obj runtime.Object) (*ObjectReference, error) {
if err != nil {
return nil, err
}
version := versionFromSelfLink.FindStringSubmatch(accessor.SelfLink())
version := versionFromSelfLink.FindStringSubmatch(meta.SelfLink())
if len(version) < 2 {
return nil, fmt.Errorf("unexpected self link format: %v", accessor.SelfLink())
return nil, fmt.Errorf("unexpected self link format: %v", meta.SelfLink())
}
return &ObjectReference{
Kind: kind,
APIVersion: version[1],
// TODO: correct Name and UID when TypeMeta makes a distinction
Name: accessor.Name(),
UID: accessor.UID(),
ResourceVersion: accessor.ResourceVersion(),
Name: meta.Name(),
UID: meta.UID(),
ResourceVersion: meta.ResourceVersion(),
}, nil
}

View File

@ -101,7 +101,7 @@ var apiObjectFuzzer = fuzz.New().NilChance(.5).NumElements(1, 1).Funcs(
func runTest(t *testing.T, codec runtime.Codec, source runtime.Object) {
name := reflect.TypeOf(source).Elem().Name()
apiObjectFuzzer.Fuzz(source)
j, err := meta.FindAccessor(source)
j, err := meta.Accessor(source)
if err != nil {
t.Fatalf("Unexpected error %v for %#v", err, source)
}
@ -160,7 +160,7 @@ func TestTypes(t *testing.T) {
t.Errorf("Couldn't make a %v? %v", kind, err)
continue
}
if _, err := meta.FindAccessor(item); err != nil {
if _, err := meta.Accessor(item); err != nil {
t.Logf("%s is not a TypeMeta and cannot be round tripped: %v", kind, err)
continue
}

View File

@ -79,12 +79,12 @@ func (r *Reflector) listAndWatch() {
glog.Errorf("Failed to list %v: %v", r.expectedType, err)
return
}
jsonBase, err := meta.FindAccessor(list)
meta, err := meta.Accessor(list)
if err != nil {
glog.Errorf("Unable to understand list result %#v", list)
return
}
resourceVersion = jsonBase.ResourceVersion()
resourceVersion = meta.ResourceVersion()
items, err := runtime.ExtractList(list)
if err != nil {
glog.Errorf("Unable to understand list result %#v (%v)", list, err)
@ -113,11 +113,11 @@ func (r *Reflector) listAndWatch() {
func (r *Reflector) syncWith(items []runtime.Object) error {
found := map[string]interface{}{}
for _, item := range items {
jsonBase, err := meta.FindAccessor(item)
meta, err := meta.Accessor(item)
if err != nil {
return fmt.Errorf("unexpected item in list: %v", err)
}
found[jsonBase.Name()] = item
found[meta.Name()] = item
}
r.store.Replace(found)
@ -140,25 +140,25 @@ func (r *Reflector) watchHandler(w watch.Interface, resourceVersion *string) err
glog.Errorf("expected type %v, but watch event object had type %v", e, a)
continue
}
jsonBase, err := meta.FindAccessor(event.Object)
meta, err := meta.Accessor(event.Object)
if err != nil {
glog.Errorf("unable to understand watch event %#v", event)
continue
}
switch event.Type {
case watch.Added:
r.store.Add(jsonBase.Name(), event.Object)
r.store.Add(meta.Name(), event.Object)
case watch.Modified:
r.store.Update(jsonBase.Name(), event.Object)
r.store.Update(meta.Name(), event.Object)
case watch.Deleted:
// TODO: Will any consumers need access to the "last known
// state", which is passed in event.Object? If so, may need
// to change this.
r.store.Delete(jsonBase.Name())
r.store.Delete(meta.Name())
default:
glog.Errorf("unable to understand watch event %#v", event)
}
*resourceVersion = jsonBase.ResourceVersion()
*resourceVersion = meta.ResourceVersion()
eventCount++
}

View File

@ -110,11 +110,11 @@ func doUpdate(c *client.RESTClient, resource string, obj runtime.Object) (string
// Update the object we are trying to send to the server with the
// correct resource version.
typeMeta, err := meta.FindAccessor(obj)
meta, err := meta.Accessor(obj)
if err != nil {
return "", err
}
typeMeta.SetResourceVersion(version)
meta.SetResourceVersion(version)
// Convert object with updated resourceVersion to data for PUT.
data, err := c.Codec.Encode(obj)
@ -150,17 +150,17 @@ func doDelete(c *client.RESTClient, resource string, obj runtime.Object) (string
}
func getIDFromObj(obj runtime.Object) (string, error) {
typeMeta, err := meta.FindAccessor(obj)
meta, err := meta.Accessor(obj)
if err != nil {
return "", err
}
return typeMeta.Name(), nil
return meta.Name(), nil
}
func getResourceVersionFromObj(obj runtime.Object) (string, error) {
typeMeta, err := meta.FindAccessor(obj)
meta, err := meta.Accessor(obj)
if err != nil {
return "", err
}
return typeMeta.ResourceVersion(), nil
return meta.ResourceVersion(), nil
}