mirror of
https://github.com/josmo/drone-rancher.git
synced 2026-06-16 14:50:35 +08:00
136 lines
2.8 KiB
Go
136 lines
2.8 KiB
Go
package api
|
|
|
|
import (
|
|
"encoding/json"
|
|
"errors"
|
|
"reflect"
|
|
|
|
"github.com/rancher/go-rancher/client"
|
|
)
|
|
|
|
func toMap(obj interface{}) (map[string]interface{}, error) {
|
|
result := map[string]interface{}{}
|
|
bytes, err := json.Marshal(obj)
|
|
if err != nil {
|
|
return result, err
|
|
}
|
|
|
|
err = json.Unmarshal(bytes, &result)
|
|
return result, err
|
|
}
|
|
|
|
func getEmbedded(obj interface{}, checkType reflect.Type) interface{} {
|
|
val := reflect.ValueOf(obj)
|
|
for val.Kind() == reflect.Ptr || val.Kind() == reflect.Interface {
|
|
val = val.Elem()
|
|
}
|
|
|
|
if val.Kind() != reflect.Struct {
|
|
panic("Passed type is not a struct got: " + val.Kind().String())
|
|
}
|
|
|
|
t := val.Type()
|
|
for i := 0; i < val.NumField(); i++ {
|
|
if t.Field(i).Anonymous && t.Field(i).Type == checkType {
|
|
if !val.Field(i).CanAddr() {
|
|
panic("Field " + t.Field(i).Name + " is not addressable, pass pointer")
|
|
}
|
|
return val.Field(i).Addr().Interface()
|
|
}
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
func getCollection(obj interface{}) *client.Collection {
|
|
val := getEmbedded(obj, reflect.TypeOf(client.Collection{}))
|
|
if val == nil {
|
|
return nil
|
|
}
|
|
return val.(*client.Collection)
|
|
}
|
|
|
|
func getResource(obj interface{}) *client.Resource {
|
|
r, ok := obj.(*client.Resource)
|
|
if ok {
|
|
return r
|
|
}
|
|
rObj, ok := obj.(client.Resource)
|
|
if ok {
|
|
return &rObj
|
|
}
|
|
val := getEmbedded(obj, reflect.TypeOf(client.Resource{}))
|
|
if val == nil {
|
|
return nil
|
|
}
|
|
return val.(*client.Resource)
|
|
}
|
|
|
|
func CollectionToMap(obj interface{}, schemas *client.Schemas) (map[string]interface{}, []map[string]interface{}, error) {
|
|
result := map[string]interface{}{}
|
|
data := []map[string]interface{}{}
|
|
if obj == nil {
|
|
return result, data, nil
|
|
}
|
|
|
|
c := getCollection(obj)
|
|
if c == nil {
|
|
return result, data, errors.New("value is not a Collection")
|
|
}
|
|
|
|
val := reflect.ValueOf(obj)
|
|
if val.Kind() == reflect.Ptr {
|
|
val = val.Elem()
|
|
}
|
|
|
|
val = val.FieldByName("Data")
|
|
for i := 0; i < val.Len(); i++ {
|
|
obj := val.Index(i)
|
|
if obj.Kind() != reflect.Ptr && obj.Kind() != reflect.Interface {
|
|
obj = obj.Addr()
|
|
}
|
|
dataObj, err := ResourceToMap(obj.Interface(), schemas)
|
|
if err != nil {
|
|
return result, data, err
|
|
}
|
|
|
|
data = append(data, dataObj)
|
|
}
|
|
|
|
collectionMap, err := toMap(obj)
|
|
if err != nil {
|
|
return result, data, err
|
|
}
|
|
|
|
collectionMap["data"] = data
|
|
return collectionMap, data, nil
|
|
}
|
|
|
|
func ResourceToMap(obj interface{}, schemas *client.Schemas) (map[string]interface{}, error) {
|
|
result := map[string]interface{}{}
|
|
if obj == nil {
|
|
return result, nil
|
|
}
|
|
|
|
resource := getResource(obj)
|
|
if resource == nil {
|
|
return result, errors.New("value is not a Resource")
|
|
}
|
|
|
|
objMap, err := toMap(obj)
|
|
if err != nil {
|
|
return result, err
|
|
}
|
|
|
|
schema := schemas.Schema(resource.Type)
|
|
for k, v := range objMap {
|
|
_, ok := schema.CheckField(k)
|
|
if !ok {
|
|
continue
|
|
}
|
|
result[k] = v
|
|
}
|
|
|
|
return result, nil
|
|
}
|