/
util.go
108 lines (86 loc) · 2.6 KB
/
util.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
package globalid
import (
"reflect"
"github.com/sensu/sensu-go/types"
)
//
// Standard ID Components
//
// NamedComponents adds Name method that returns first element of
// global ID's uniqueComponents.
type NamedComponents struct{ StandardComponents }
// Name method returns first element of global ID's uniqueComponents. Congurent
// with most Sensu records Check#Name, Entity#ID, Asset#name, etc.
func (n NamedComponents) Name() string {
return n.uniqueComponent
}
//
// Standard Translator
//
type encoderFunc func(interface{}) Components
type decoderFunc func(StandardComponents) Components
type commonTranslator struct {
name string
isResponsibleFunc func(interface{}) bool
encodeFunc encoderFunc
decodeFunc decoderFunc
}
func (r commonTranslator) ForResourceNamed() string {
return r.name
}
func (r commonTranslator) IsResponsible(record interface{}) bool {
return r.isResponsibleFunc(record)
}
func (r commonTranslator) Encode(record interface{}) Components {
components := r.encodeFunc(record)
return components
}
func (r commonTranslator) EncodeToString(record interface{}) string {
components := r.Encode(record)
return components.String()
}
func (r commonTranslator) Decode(components StandardComponents) Components {
return r.decodeFunc(components)
}
//
// Helpers
//
func addMultitenantFields(c *StandardComponents, r types.MultitenantResource) {
c.namespace = r.GetNamespace()
}
// newComponentsWith returns new instance of StandardComponents w/ name and ids
func newComponentsWith(resourceName string, uids ...string) StandardComponents {
var t, name string
if len(uids) > 1 {
t, name = uids[0], uids[1]
} else {
name = uids[0]
}
return StandardComponents{
resource: resourceName,
resourceType: t,
uniqueComponent: name,
}
}
// standardDecoder instantiates new NamedComponents composite.
func standardDecoder(components StandardComponents) Components {
return NamedComponents{components}
}
// standardEncoder encodes record given name and unique field name
func standardEncoder(name string, fNames ...string) encoderFunc {
return func(record interface{}) Components {
// Retrieve the value of the specified field
fVal := reflect.ValueOf(record)
for _, fName := range fNames {
fVal = reflect.Indirect(fVal)
fVal = fVal.FieldByName(fName)
}
// Add string value of field to global id components
components := newComponentsWith(name, fVal.String())
// Add namespace to global id components
if multiRecord, ok := record.(types.MultitenantResource); ok {
addMultitenantFields(&components, multiRecord)
}
return components
}
}