...
1
2 package inject
3
4 import (
5 "fmt"
6 "reflect"
7 )
8
9
10
11 type Injector interface {
12 Applicator
13 Invoker
14 TypeMapper
15
16
17
18 SetParent(Injector)
19 }
20
21
22 type Applicator interface {
23
24
25
26 Apply(interface{}) error
27 }
28
29
30 type Invoker interface {
31
32
33
34
35 Invoke(interface{}) ([]reflect.Value, error)
36 }
37
38
39 type TypeMapper interface {
40
41 Map(interface{}) TypeMapper
42
43
44
45 MapTo(interface{}, interface{}) TypeMapper
46
47
48
49 Set(reflect.Type, reflect.Value) TypeMapper
50
51
52 Get(reflect.Type) reflect.Value
53 }
54
55 type injector struct {
56 values map[reflect.Type]reflect.Value
57 parent Injector
58 }
59
60
61
62 func InterfaceOf(value interface{}) reflect.Type {
63 t := reflect.TypeOf(value)
64
65 for t.Kind() == reflect.Ptr {
66 t = t.Elem()
67 }
68
69 if t.Kind() != reflect.Interface {
70 panic("Called inject.InterfaceOf with a value that is not a pointer to an interface. (*MyInterface)(nil)")
71 }
72
73 return t
74 }
75
76
77 func New() Injector {
78 return &injector{
79 values: make(map[reflect.Type]reflect.Value),
80 }
81 }
82
83
84
85
86
87
88 func (inj *injector) Invoke(f interface{}) ([]reflect.Value, error) {
89 t := reflect.TypeOf(f)
90
91 var in = make([]reflect.Value, t.NumIn())
92 for i := 0; i < t.NumIn(); i++ {
93 argType := t.In(i)
94 val := inj.Get(argType)
95 if !val.IsValid() {
96 return nil, fmt.Errorf("Value not found for type %v", argType)
97 }
98
99 in[i] = val
100 }
101
102 return reflect.ValueOf(f).Call(in), nil
103 }
104
105
106
107
108 func (inj *injector) Apply(val interface{}) error {
109 v := reflect.ValueOf(val)
110
111 for v.Kind() == reflect.Ptr {
112 v = v.Elem()
113 }
114
115 if v.Kind() != reflect.Struct {
116 return nil
117 }
118
119 t := v.Type()
120
121 for i := 0; i < v.NumField(); i++ {
122 f := v.Field(i)
123 structField := t.Field(i)
124 if f.CanSet() && (structField.Tag == "inject" || structField.Tag.Get("inject") != "") {
125 ft := f.Type()
126 v := inj.Get(ft)
127 if !v.IsValid() {
128 return fmt.Errorf("Value not found for type %v", ft)
129 }
130
131 f.Set(v)
132 }
133
134 }
135
136 return nil
137 }
138
139
140
141 func (i *injector) Map(val interface{}) TypeMapper {
142 i.values[reflect.TypeOf(val)] = reflect.ValueOf(val)
143 return i
144 }
145
146 func (i *injector) MapTo(val interface{}, ifacePtr interface{}) TypeMapper {
147 i.values[InterfaceOf(ifacePtr)] = reflect.ValueOf(val)
148 return i
149 }
150
151
152
153 func (i *injector) Set(typ reflect.Type, val reflect.Value) TypeMapper {
154 i.values[typ] = val
155 return i
156 }
157
158 func (i *injector) Get(t reflect.Type) reflect.Value {
159 val := i.values[t]
160
161 if val.IsValid() {
162 return val
163 }
164
165
166
167 if t.Kind() == reflect.Interface {
168 for k, v := range i.values {
169 if k.Implements(t) {
170 val = v
171 break
172 }
173 }
174 }
175
176
177 if !val.IsValid() && i.parent != nil {
178 val = i.parent.Get(t)
179 }
180
181 return val
182
183 }
184
185 func (i *injector) SetParent(parent Injector) {
186 i.parent = parent
187 }
188
View as plain text