Skip to content

Commit

Permalink
Merge #57
Browse files Browse the repository at this point in the history
57: Fix bug with partially initialized graph. Rename interface Depender r=48d90782 a=48d90782

Fixes #53 
Fixes #55

Co-authored-by: Valery Piashchynski <piashchynski_valery@hotmail.com>
  • Loading branch information
bors[bot] and rustatian authored Oct 28, 2020
2 parents 74d079e + 27cf040 commit 035d73a
Show file tree
Hide file tree
Showing 106 changed files with 270 additions and 835 deletions.
Empty file modified .github/dependabot.yml
100644 → 100755
Empty file.
Empty file modified .github/workflows/ci-build.yml
100644 → 100755
Empty file.
Empty file modified .github/workflows/codeql-analysis.yml
100644 → 100755
Empty file.
Empty file modified .gitignore
100644 → 100755
Empty file.
Empty file modified .golangci.yml
100644 → 100755
Empty file.
Empty file modified Makefile
100644 → 100755
Empty file.
8 changes: 4 additions & 4 deletions README.md
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -82,15 +82,15 @@ type (
Provides() []interface{}
}

// Depender declares the ability to accept the plugins which match the provided method signature.
Depender interface {
Depends() []interface{}
// Collector declares the ability to accept the plugins which match the provided method signature.
Collector interface {
Collects() []interface{}
}
)
```
Order is the following:
1. `Init() error` - is mandatory to implement. In your structure (which you pass to Endure), you should have this method as a receiver. It can accept as parameter any passed to the `Endure` structure (see samples) or interface (with limitations).
3. `Service` - is optional to implement. It has 2 main methods - `Serve` which should run the plugin and return initialized golang channel with errors, and `Stop` to shut down the plugin.
4. `Provider` - is optional to implement. It is used to provide some dependency if you need to extend your struct.
5. `Depender` - is optional to implement. It is used to mark a structure (vertex) as some struct dependency. It can accept interfaces which implement the caller.
5. `Collector` - is optional to implement. It is used to mark a structure (vertex) as some struct dependency. It can accept interfaces which implement the caller.
6. `Named` - is optional to implement. This is a special kind of interface which provides the name of the struct (plugin, vertex) to the caller. Is useful in logger (for example) to know user-friendly plugin name.
Empty file modified bors.toml
100644 → 100755
Empty file.
30 changes: 15 additions & 15 deletions calculate_deps.go
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@ import (
"fmt"
"reflect"

"github.com/spiral/endure/errors"
"github.com/spiral/endure/structures"
"github.com/spiral/errors"
"go.uber.org/zap"
)

Expand Down Expand Up @@ -90,7 +90,7 @@ func (e *Endure) addEdges() error {
init, _ := reflect.TypeOf(vrtx.Iface).MethodByName(InitMethodName)

if init.Type == nil {
e.logger.Fatal("init method is absent in struct", zap.String("vertexId", vertexID))
e.logger.Fatal("init method is absent in struct", zap.String("vertex id", vertexID))
return errors.E(Op, fmt.Errorf("init method is absent in struct"))
}

Expand All @@ -103,13 +103,13 @@ func (e *Endure) addEdges() error {
5. FunctionName of the dependencies which we should found
We add 3 and 4 points to the Vertex
*/
err := e.addDependersDeps(vertexID, vrtx.Iface)
err := e.addCollectorsDeps(vertexID, vrtx.Iface)
if err != nil {
return errors.E(Op, err)
}

/*
At this step we know (and build) all dependencies via the Depends interface and connected all providers
At this step we know (and build) all dependencies via the Collects interface and connected all providers
to it's dependencies.
The next step is to calculate dependencies provided by the Init() method
for example S1.Init(foo2.DB) S1 --> foo2.S2 (not foo2.DB, because vertex which provides foo2.DB is foo2.S2)
Expand All @@ -123,10 +123,10 @@ func (e *Endure) addEdges() error {
return nil
}

func (e *Endure) addDependersDeps(vertexID string, vertex interface{}) error {
const Op = "add_dependers_deps"
if register, ok := vertex.(Depender); ok {
for _, fn := range register.Depends() {
func (e *Endure) addCollectorsDeps(vertexID string, vertex interface{}) error {
const Op = "add_collectors_deps"
if register, ok := vertex.(Collector); ok {
for _, fn := range register.Collects() {
// what type it might depend on?
argsTypes, err := argType(fn)
if err != nil {
Expand All @@ -144,7 +144,7 @@ func (e *Endure) addDependersDeps(vertexID string, vertex interface{}) error {
if vertexID == atStr {
continue
}
// depends at interface via Dependers
// depends at interface via Collectors
/*
In this case we should do the following:
1. Find all types, which implement this interface
Expand All @@ -167,11 +167,11 @@ func (e *Endure) addDependersDeps(vertexID string, vertex interface{}) error {
// vertex - S4 func

// we store pointer in the Deps structure in the isRef field
err = e.graph.AddDep(vertexID, removePointerAsterisk(atStr), structures.Depends, isReference(at), at.Kind())
err = e.graph.AddDep(vertexID, removePointerAsterisk(atStr), structures.Collects, isReference(at), at.Kind())
if err != nil {
return errors.E(Op, err)
}
e.logger.Debug("adding dependency via Depends()", zap.String("vertex id", vertexID), zap.String("depends", atStr))
e.logger.Debug("adding dependency via Collects()", zap.String("vertex id", vertexID), zap.String("depends", atStr))
}

// get the Vertex from the graph (gVertex)
Expand All @@ -180,13 +180,13 @@ func (e *Endure) addDependersDeps(vertexID string, vertex interface{}) error {
gVertex.Provides = make(map[string]structures.ProvidedEntry)
}

if gVertex.Meta.FnsDependerToInvoke == nil {
gVertex.Meta.FnsDependerToInvoke = make([]string, 0, 5)
if gVertex.Meta.FnsCollectorToInvoke == nil {
gVertex.Meta.FnsCollectorToInvoke = make([]string, 0, 5)
}

e.logger.Debug("appending depender function to invoke later", zap.String("vertex id", vertexID), zap.String("function name", getFunctionName(fn)))
e.logger.Debug("appending collector function to invoke later", zap.String("vertex id", vertexID), zap.String("function name", getFunctionName(fn)))

gVertex.Meta.FnsDependerToInvoke = append(gVertex.Meta.FnsDependerToInvoke, getFunctionName(fn))
gVertex.Meta.FnsCollectorToInvoke = append(gVertex.Meta.FnsCollectorToInvoke, getFunctionName(fn))
}
}

Expand Down
11 changes: 6 additions & 5 deletions container.go
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,13 @@ package endure
// InitMethodName is the function name for the reflection
const InitMethodName = "Init"

// ServeMethodName
// ServeMethodName is the function name for the Serve
const ServeMethodName = "Serve"

// Stop is the function name for the reflection to Stop the service
// StopMethodName is the function name for the reflection to Stop the service
const StopMethodName = "Stop"

// Result is the information which endure send to the user
type Result struct {
Error error
VertexID string
Expand Down Expand Up @@ -57,8 +58,8 @@ type (
Provides() []interface{}
}

// Depender declares the ability to accept the plugins which match the provided method signature.
Depender interface {
Depends() []interface{}
// Collector declares the ability to accept the plugins which match the provided method signature.
Collector interface {
Collects() []interface{}
}
)
15 changes: 10 additions & 5 deletions endure.go
100644 → 100755
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@ import (
"sync"
"time"

"github.com/spiral/endure/errors"
"github.com/spiral/endure/structures"
"github.com/spiral/errors"
"go.uber.org/zap"
"go.uber.org/zap/zapcore"
)
Expand Down Expand Up @@ -176,9 +176,7 @@ func Visualize(print bool) Options {
}
}

// Depender depends the dependencies
// name is a name of the dependency, for example - S2
// vertex is a value -> pointer to the structure
// Register registers the dependencies in the Endure graph without invoking any methods
func (e *Endure) Register(vertex interface{}) error {
const op = errors.Op("Register")
t := reflect.TypeOf(vertex)
Expand All @@ -188,7 +186,7 @@ func (e *Endure) Register(vertex interface{}) error {
return errors.E(op, errors.Register, errors.Errorf("you should pass pointer to the structure instead of value"))
}

/* Depender the type
/* Collector the type
Information we know at this step is:
1. vertexID
2. Vertex structure value (interface)
Expand Down Expand Up @@ -265,7 +263,12 @@ func (e *Endure) Init() error {
return nil
}

// Serve starts serving the graph
// This is the initial serve, if error produced immediately in the initial serve, endure will traverse deps back, call stop and exit
func (e *Endure) Serve() (<-chan *Result, error) {
e.mutex.Lock()
defer e.mutex.Unlock()

const op = errors.Op("Serve")
e.startMainThread()

Expand All @@ -281,6 +284,7 @@ func (e *Endure) Serve() (<-chan *Result, error) {
atLeastOne = true
err := e.serve(nCopy)
if err != nil {
e.traverseBackStop(nCopy)
return nil, errors.E(op, errors.Serve, err)
}
nCopy = nCopy.Next
Expand All @@ -292,6 +296,7 @@ func (e *Endure) Serve() (<-chan *Result, error) {
return e.userResultsCh, nil
}

// Stop stops the execution and call Stop on every vertex
func (e *Endure) Stop() error {
e.mutex.Lock()
defer e.mutex.Unlock()
Expand Down
10 changes: 0 additions & 10 deletions errors/debug_cap.go

This file was deleted.

116 changes: 0 additions & 116 deletions errors/debug_stack.go

This file was deleted.

Loading

0 comments on commit 035d73a

Please sign in to comment.