Skip to content

Commit b988591

Browse files
author
Valery Piashchynski
committed
Internal improvements
1 parent c046c2a commit b988591

File tree

7 files changed

+171
-144
lines changed

7 files changed

+171
-144
lines changed

calculate_deps.go

Lines changed: 140 additions & 118 deletions
Original file line numberDiff line numberDiff line change
@@ -97,14 +97,14 @@ func (e *Endure) implProvidesPath(vertexID string, vertex interface{}) error {
9797
return nil
9898
}
9999

100-
func (e *Endure) addCollectorsDeps(vertexID string, vertex interface{}) error {
100+
func (e *Endure) addCollectorsDeps(vertex *Vertex) error {
101101
// hot path
102-
if _, ok := vertex.(Collector); !ok {
102+
if _, ok := vertex.Iface.(Collector); !ok {
103103
return nil
104104
}
105105

106106
// vertex implements Collector interface
107-
return e.implCollectorPath(vertexID, vertex)
107+
return e.implCollectorPath(vertex)
108108
}
109109

110110
func (e *Endure) walk(params []reflect.Type, v *Vertex) bool {
@@ -127,9 +127,10 @@ func (e *Endure) walk(params []reflect.Type, v *Vertex) bool {
127127
return true
128128
}
129129

130-
func (e *Endure) implCollectorPath(vertexID string, vertex interface{}) error {
130+
func (e *Endure) implCollectorPath(vertex *Vertex) error {
131+
// vertexID string, vertex interface{} same vertex
131132
const op = errors.Op("add_collectors_deps")
132-
collector := vertex.(Collector)
133+
collector := vertex.Iface.(Collector)
133134
// range Collectors functions
134135
for _, fn := range collector.Collects() {
135136
haveInterfaceDeps := false
@@ -145,149 +146,170 @@ func (e *Endure) implCollectorPath(vertexID string, vertex interface{}) error {
145146
// filter out interfaces, leave only structs
146147
for i := 0; i < len(e.graph.Vertices); i++ {
147148
// skip self
148-
if e.graph.Vertices[i].ID == vertexID {
149+
if e.graph.Vertices[i].ID == vertex.ID {
149150
continue
150151
}
151152
if e.walk(params, e.graph.Vertices[i]) == true {
152153
compatible = append(compatible, e.graph.Vertices[i])
153154
// set, that we have interface deps
154155
haveInterfaceDeps = true
156+
e.logger.Info("vertex is compatible with Collects", zap.String("vertex id", e.graph.Vertices[i].ID), zap.String("collects from vertex", vertex.ID))
157+
continue
155158
}
159+
e.logger.Info("vertex is not compatible with Collects", zap.String("vertex id", e.graph.Vertices[i].ID), zap.String("collects from vertex", vertex.ID))
160+
}
161+
162+
if len(compatible) == 0 && haveInterfaceDeps {
163+
e.logger.Info("no compatible vertices found", zap.String("collects from vertex", vertex.ID))
164+
return nil
156165
}
157-
// traverse
166+
// process mixed deps (interfaces + structs)
158167
if haveInterfaceDeps {
159-
for _, compat := range compatible {
160-
// add vertex itself
161-
cp := CollectorEntry{
162-
in: make([]In, 0, 0),
163-
fn: getFunctionName(fn),
164-
}
165-
cp.in = append(cp.in, In{
166-
in: reflect.ValueOf(vertex),
167-
dep: vertexID,
168-
})
168+
return e.processInterfaceDeps(compatible, fn, vertex, params)
169+
}
170+
// process only struct deps if not interfaces were found
171+
return e.processStructDeps(fn, vertex, params)
172+
}
173+
return nil
174+
}
169175

170-
for _, param := range params {
171-
// check if type is primitive type
172-
if isPrimitive(param.String()) {
173-
e.logger.Panic("primitive type in the function parameters", zap.String("vertex id", vertexID), zap.String("type", param.String()))
174-
}
176+
func (e *Endure) processInterfaceDeps(compatible Vertices, fn interface{}, vertex *Vertex, params []reflect.Type) error {
177+
const op = errors.Op("process interface deps")
178+
for _, compat := range compatible {
179+
// add vertex itself
180+
cp := CollectorEntry{
181+
in: make([]In, 0, 0),
182+
fn: getFunctionName(fn),
183+
}
184+
cp.in = append(cp.in, In{
185+
in: reflect.ValueOf(vertex.Iface),
186+
dep: vertex.ID,
187+
})
188+
189+
for _, param := range params {
190+
// check if type is primitive type
191+
if isPrimitive(param.String()) {
192+
e.logger.Panic("primitive type in the function parameters", zap.String("vertex id", vertex.ID), zap.String("type", param.String()))
193+
}
175194

176-
paramStr := param.String()
177-
if vertexID == paramStr {
178-
continue
179-
}
195+
paramStr := param.String()
196+
if vertex.ID == paramStr {
197+
continue
198+
}
180199

181-
switch param.Kind() {
182-
case reflect.Ptr:
183-
if param.Elem().Kind() == reflect.Struct {
184-
dep := e.graph.VerticesMap[(removePointerAsterisk(param.String()))]
185-
if dep == nil {
186-
panic("can't find provider")
187-
}
188-
189-
cp.in = append(cp.in, In{
190-
in: reflect.ValueOf(dep.Iface),
191-
dep: dep.ID,
192-
})
193-
194-
err = e.graph.AddDep(vertexID, removePointerAsterisk(dep.ID), Collects, isReference(param), param.Kind())
195-
if err != nil {
196-
return errors.E(op, err)
197-
}
198-
}
199-
case reflect.Interface:
200-
cp.in = append(cp.in, In{
201-
in: reflect.ValueOf(compat.Iface),
202-
dep: compat.ID,
203-
})
204-
205-
err = e.graph.AddDep(vertexID, removePointerAsterisk(compat.ID), Collects, isReference(param), param.Kind())
206-
if err != nil {
207-
return errors.E(op, err)
208-
}
209-
210-
case reflect.Struct:
211-
dep := e.graph.VerticesMap[(removePointerAsterisk(param.String()))]
212-
if dep == nil {
213-
panic("can't find provider")
214-
}
215-
216-
cp.in = append(cp.in, In{
217-
in: reflect.ValueOf(dep.Iface),
218-
dep: dep.ID,
219-
})
220-
221-
err = e.graph.AddDep(vertexID, removePointerAsterisk(dep.ID), Collects, isReference(param), param.Kind())
222-
if err != nil {
223-
return errors.E(op, err)
224-
}
200+
switch param.Kind() {
201+
case reflect.Ptr:
202+
if param.Elem().Kind() == reflect.Struct {
203+
dep := e.graph.VerticesMap[(removePointerAsterisk(param.String()))]
204+
if dep == nil {
205+
return errors.E(op, errors.Errorf("can't find provider for the struct parameter: %s", removePointerAsterisk(param.String())))
225206
}
226-
}
227-
v := e.graph.GetVertex(vertexID)
228-
v.Meta.FnsCollectorToInvoke = append(v.Meta.FnsCollectorToInvoke, cp)
229-
}
230-
} else {
231-
cp := CollectorEntry{
232-
in: make([]In, 0, 0),
233-
fn: getFunctionName(fn),
234-
}
235-
cp.in = append(cp.in, In{
236-
in: reflect.ValueOf(vertex),
237-
dep: vertexID,
238-
})
239207

240-
for _, param := range params {
241-
// check if type is primitive type
242-
if isPrimitive(param.String()) {
243-
e.logger.Panic("primitive type in the function parameters", zap.String("vertex id", vertexID), zap.String("type", param.String()))
208+
cp.in = append(cp.in, In{
209+
in: reflect.ValueOf(dep.Iface),
210+
dep: dep.ID,
211+
})
212+
213+
err := e.graph.AddDep(vertex.ID, removePointerAsterisk(dep.ID), Collects, isReference(param), param.Kind())
214+
if err != nil {
215+
return errors.E(op, err)
216+
}
244217
}
218+
case reflect.Interface:
219+
cp.in = append(cp.in, In{
220+
in: reflect.ValueOf(compat.Iface),
221+
dep: compat.ID,
222+
})
245223

246-
// skip self
247-
paramStr := param.String()
248-
if vertexID == paramStr {
249-
continue
224+
err := e.graph.AddDep(vertex.ID, removePointerAsterisk(compat.ID), Collects, isReference(param), param.Kind())
225+
if err != nil {
226+
return errors.E(op, err)
250227
}
251228

229+
case reflect.Struct:
252230
dep := e.graph.VerticesMap[(removePointerAsterisk(param.String()))]
253231
if dep == nil {
254-
depIds := e.graph.FindProviders(removePointerAsterisk(paramStr))
255-
if len(depIds) == 0 {
256-
panic("can't find provider for dep")
257-
}
258-
dep = depIds[0]
259-
for k, v := range dep.Provides {
260-
if k == removePointerAsterisk(paramStr) {
261-
cp.in = append(cp.in, In{
262-
in: reflect.Zero(reflect.TypeOf(v)),
263-
dep: k,
264-
})
265-
}
266-
}
267-
} else {
268-
cp.in = append(cp.in, In{
269-
in: reflect.ValueOf(dep.Iface),
270-
dep: dep.ID,
271-
})
232+
return errors.E(op, errors.Errorf("can't find provider for the struct parameter: %s", removePointerAsterisk(param.String())))
272233
}
273234

274-
tmpIsRef := isReference(param)
275-
tmpValue := reflect.ValueOf(dep.Iface)
276-
e.graph.AddGlobalProvider(removePointerAsterisk(paramStr), tmpValue)
277-
e.graph.VerticesMap[dep.ID].AddProvider(removePointerAsterisk(paramStr), tmpValue, tmpIsRef, param.Kind())
235+
cp.in = append(cp.in, In{
236+
in: reflect.ValueOf(dep.Iface),
237+
dep: dep.ID,
238+
})
278239

279-
err = e.graph.AddDep(vertexID, removePointerAsterisk(paramStr), Collects, isReference(param), param.Kind())
240+
err := e.graph.AddDep(vertex.ID, removePointerAsterisk(dep.ID), Collects, isReference(param), param.Kind())
280241
if err != nil {
281242
return errors.E(op, err)
282243
}
244+
}
245+
}
246+
vertex.Meta.CollectorEntries = append(vertex.Meta.CollectorEntries, cp)
247+
}
248+
249+
return nil
250+
}
251+
252+
func (e *Endure) processStructDeps(fn interface{}, vertex *Vertex, params []reflect.Type) error {
253+
const op = errors.Op("process struct deps")
254+
// process only struct deps
255+
cp := CollectorEntry{
256+
in: make([]In, 0, 0),
257+
fn: getFunctionName(fn),
258+
}
259+
cp.in = append(cp.in, In{
260+
in: reflect.ValueOf(vertex.Iface),
261+
dep: vertex.ID,
262+
})
263+
264+
for _, param := range params {
265+
// check if type is primitive type
266+
if isPrimitive(param.String()) {
267+
e.logger.Panic("primitive type in the function parameters", zap.String("vertex id", vertex.ID), zap.String("type", param.String()))
268+
}
283269

284-
e.logger.Debug("adding dependency via Collects()", zap.String("vertex id", vertexID), zap.String("depends", paramStr))
270+
// skip self
271+
paramStr := param.String()
272+
if vertex.ID == paramStr {
273+
continue
274+
}
275+
276+
dep := e.graph.VerticesMap[(removePointerAsterisk(param.String()))]
277+
if dep == nil {
278+
depIds := e.graph.FindProviders(removePointerAsterisk(paramStr))
279+
if len(depIds) == 0 {
280+
e.logger.Warn("can't find any provider for the dependency, collector function on the vertex will not be invoked", zap.String("dep id", removePointerAsterisk(param.String())), zap.String("vertexId", vertex.ID))
281+
return nil
285282
}
283+
dep = depIds[0]
284+
for k, v := range dep.Provides {
285+
if k == removePointerAsterisk(paramStr) {
286+
cp.in = append(cp.in, In{
287+
in: reflect.Zero(reflect.TypeOf(v)),
288+
dep: k,
289+
})
290+
}
291+
}
292+
} else {
293+
cp.in = append(cp.in, In{
294+
in: reflect.ValueOf(dep.Iface),
295+
dep: dep.ID,
296+
})
297+
}
298+
299+
tmpIsRef := isReference(param)
300+
tmpValue := reflect.ValueOf(dep.Iface)
301+
e.graph.AddGlobalProvider(removePointerAsterisk(paramStr), tmpValue)
302+
e.graph.VerticesMap[dep.ID].AddProvider(removePointerAsterisk(paramStr), tmpValue, tmpIsRef, param.Kind())
286303

287-
v := e.graph.GetVertex(vertexID)
288-
v.Meta.FnsCollectorToInvoke = append(v.Meta.FnsCollectorToInvoke, cp)
304+
err := e.graph.AddDep(vertex.ID, removePointerAsterisk(paramStr), Collects, isReference(param), param.Kind())
305+
if err != nil {
306+
return errors.E(op, err)
289307
}
308+
309+
e.logger.Debug("adding dependency via Collects()", zap.String("vertex id", vertex.ID), zap.String("depends", paramStr))
290310
}
311+
312+
vertex.Meta.CollectorEntries = append(vertex.Meta.CollectorEntries, cp)
291313
return nil
292314
}
293315

@@ -314,7 +336,7 @@ func (e *Endure) addEdges() error {
314336
5. FunctionName of the dependencies which we should found
315337
We add 3 and 4 points to the Vertex
316338
*/
317-
err := e.addCollectorsDeps(vertexID, vrtx.Iface)
339+
err := e.addCollectorsDeps(vrtx)
318340
if err != nil {
319341
return errors.E(Op, err)
320342
}

endure.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -407,4 +407,4 @@ func (e *Endure) Shutdown() error {
407407
e.logger.Info("exiting from the Endure")
408408
n := e.runList.Head
409409
return e.shutdown(n, true)
410-
}
410+
}

examples/sample_1/go.sum

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,8 @@ github.com/spiral/endure v1.0.0-beta13 h1:iz0xvAxBsHYQKpJB2IdJaAc29GCR2bEu/NPjNs
4040
github.com/spiral/endure v1.0.0-beta13/go.mod h1:Kr88l/C5sVrEiJy8cKHA2TndGdbY17wi8SH8qoYQ3XQ=
4141
github.com/spiral/endure v1.0.0-beta16 h1:URSlwsKbt755cHzN/xPPVW9GI2ETy09EFXHs2EVGPxM=
4242
github.com/spiral/endure v1.0.0-beta16/go.mod h1:qm3evrNggh26QQhwln2uH/1KJQInFZKJZeD5Yvm2k6Y=
43+
github.com/spiral/endure v1.0.0-beta17 h1:1vBTUzwHGUBOGr+4e2kTftAPyzCKOMbUtACReuMlrmc=
44+
github.com/spiral/endure v1.0.0-beta17/go.mod h1:qm3evrNggh26QQhwln2uH/1KJQInFZKJZeD5Yvm2k6Y=
4345
github.com/spiral/errors v1.0.1 h1:OyKLwQH+42hhaRYuXGzfPKCFOmawA/PYXTY9wsK99n4=
4446
github.com/spiral/errors v1.0.1/go.mod h1:SwMSZVdZkkJVgXNNafccqOaxWg0XPzVU/dEdUEInE0o=
4547
github.com/spiral/errors v1.0.2 h1:i/XMmA2VJt9sD64N4/zgQ9Y0cwlNQRLDaxOZPZV09D4=

graph.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ type Graph struct {
2929
}
3030

3131
type ProviderEntries []ProviderEntry
32+
type CollectorEntries []CollectorEntry
3233

3334
// Meta information included into the Vertex
3435
// May include:
@@ -39,8 +40,8 @@ type Meta struct {
3940
Order int
4041
// FnsProviderToInvoke is the function names to invoke if type implements Provides() interface
4142
FnsProviderToInvoke ProviderEntries
42-
// FnsCollectorToInvoke is the function names to invoke if type implements Collector() interface
43-
FnsCollectorToInvoke []CollectorEntry
43+
// CollectorEntries is the function names to invoke if type implements Collector() interface
44+
CollectorEntries CollectorEntries
4445

4546
// List of the vertex deps
4647
// foo4.DB, foo4.S4 etc.. which were found in the Init() method

init.go

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -91,25 +91,25 @@ func (e *Endure) callInitFn(init reflect.Method, vertex *Vertex) error {
9191
return errors.E(op, errors.ArgType, errors.Str("0 or less parameters for Init"))
9292
}
9393

94-
if len(vertex.Meta.FnsCollectorToInvoke) > 0 {
95-
for i := 0; i < len(vertex.Meta.FnsCollectorToInvoke); i++ {
94+
if len(vertex.Meta.CollectorEntries) > 0 {
95+
for i := 0; i < len(vertex.Meta.CollectorEntries); i++ {
9696
// try to find nil IN args and get it from global
97-
for j := 0; j < len(vertex.Meta.FnsCollectorToInvoke[i].in); j++ {
98-
if vertex.Meta.FnsCollectorToInvoke[i].in[j].in.IsZero() {
99-
global, ok := e.graph.providers[vertex.Meta.FnsCollectorToInvoke[i].in[j].dep]
97+
for j := 0; j < len(vertex.Meta.CollectorEntries[i].in); j++ {
98+
if vertex.Meta.CollectorEntries[i].in[j].in.IsZero() {
99+
global, ok := e.graph.providers[vertex.Meta.CollectorEntries[i].in[j].dep]
100100
if !ok {
101101
e.logger.Error("can't find in arg to Call Collects on the vertex", zap.String("vertex id", vertex.ID))
102102
return errors.E(op, errors.Errorf("vertex id: %s", vertex.ID))
103103
}
104-
vertex.Meta.FnsCollectorToInvoke[i].in[j].in = global
104+
vertex.Meta.CollectorEntries[i].in[j].in = global
105105
}
106106
}
107107

108-
in := make([]reflect.Value, 0, len(vertex.Meta.FnsCollectorToInvoke[i].in))
109-
for _, v := range vertex.Meta.FnsCollectorToInvoke[i].in {
108+
in := make([]reflect.Value, 0, len(vertex.Meta.CollectorEntries[i].in))
109+
for _, v := range vertex.Meta.CollectorEntries[i].in {
110110
in = append(in, v.in)
111111
}
112-
err = e.fnCallCollectors(vertex, in, vertex.Meta.FnsCollectorToInvoke[i].fn)
112+
err = e.fnCallCollectors(vertex, in, vertex.Meta.CollectorEntries[i].fn)
113113
if err != nil {
114114
return errors.E(op, errors.Traverse, err)
115115
}

0 commit comments

Comments
 (0)