iris/hero/dependency_test.go

207 lines
4.7 KiB
Go
Raw Normal View History

package hero_test
import (
"fmt"
"reflect"
"testing"
"github.com/kataras/iris/v12/context"
. "github.com/kataras/iris/v12/hero"
)
type testDependencyTest struct {
Dependency interface{}
Expected interface{}
}
func TestDependency(t *testing.T) {
var tests = []testDependencyTest{
{
Dependency: "myValue",
Expected: "myValue",
},
{
Dependency: struct{ Name string }{"name"},
Expected: struct{ Name string }{"name"},
},
{
Dependency: func(*context.Context, *Input) (reflect.Value, error) {
return reflect.ValueOf(42), nil
},
Expected: 42,
},
{
Dependency: DependencyHandler(func(*context.Context, *Input) (reflect.Value, error) {
return reflect.ValueOf(255), nil
}),
Expected: 255,
},
{
Dependency: func(*context.Context) (reflect.Value, error) {
return reflect.ValueOf("OK without Input"), nil
},
Expected: "OK without Input",
},
{
Dependency: func(*context.Context, ...string) (reflect.Value, error) {
return reflect.ValueOf("OK variadic ignored"), nil
},
Expected: "OK variadic ignored",
},
{
Dependency: func(*context.Context) reflect.Value {
return reflect.ValueOf("OK without Input and error")
},
Expected: "OK without Input and error",
},
{
Dependency: func(*context.Context, ...int) reflect.Value {
return reflect.ValueOf("OK without error and variadic ignored")
},
Expected: "OK without error and variadic ignored",
},
{
Dependency: func(*context.Context) interface{} {
return "1"
},
Expected: "1",
},
{
Dependency: func(*context.Context) interface{} {
return false
},
Expected: false,
},
}
testDependencies(t, tests)
}
// Test dependencies that depend on previous one(s).
func TestDependentDependency(t *testing.T) {
msgBody := "prefix: it is a deep dependency"
newMsgBody := msgBody + " new"
var tests = []testDependencyTest{
// test three level depth and error.
{ // 0
Dependency: &testServiceImpl{prefix: "prefix:"},
Expected: &testServiceImpl{prefix: "prefix:"},
},
{ // 1
Dependency: func(service testService) testMessage {
return testMessage{Body: service.Say("it is a deep") + " dependency"}
},
Expected: testMessage{Body: msgBody},
},
{ // 2
Dependency: func(msg testMessage) string {
return msg.Body
},
Expected: msgBody,
},
{ // 3
Dependency: func(msg testMessage) error {
return fmt.Errorf(msg.Body)
},
Expected: fmt.Errorf(msgBody),
},
// Test depend on more than one previous registered dependencies and require a before-previous one.
{ // 4
Dependency: func(body string, msg testMessage) string {
if body != msg.Body {
t.Fatalf("body[%s] != msg.Body[%s]", body, msg.Body)
}
return body + " new"
},
Expected: newMsgBody,
},
// Test dependency order by expecting the first <string> returning value and not the later-on registered dependency(#4).
// 5
{
Dependency: func(body string) string {
return body
},
Expected: newMsgBody,
},
}
testDependencies(t, tests)
}
func testDependencies(t *testing.T, tests []testDependencyTest) {
t.Helper()
c := New()
for i, tt := range tests {
d := c.Register(tt.Dependency)
if d == nil {
t.Fatalf("[%d] expected %#+v to be converted to a valid dependency", i, tt)
}
val, err := d.Handle(context.NewContext(nil), &Input{})
if expectError := isError(reflect.TypeOf(tt.Expected)); expectError {
val = reflect.ValueOf(err)
err = nil
}
if err != nil {
t.Fatalf("[%d] expected a nil error but got: %v", i, err)
}
if !val.CanInterface() {
t.Fatalf("[%d] expected output value to be accessible: %T", i, val)
}
if expected, got := fmt.Sprintf("%#+v", tt.Expected), fmt.Sprintf("%#+v", val.Interface()); expected != got {
t.Fatalf("[%d] expected return value to be:\n%s\nbut got:\n%s", i, expected, got)
}
// t.Logf("[%d] %s", i, d)
// t.Logf("[%d] output: %#+v", i, val.Interface())
}
}
func TestDependentDependencyInheritanceStatic(t *testing.T) {
// Tests the following case #1564:
// Logger
// func(Logger) S1
// ^ Should be static because Logger
// is a structure, a static dependency.
//
// func(Logger) S2
// func(S1, S2) S3
// ^ Should be marked as static dependency
// because everything that depends on are static too.
type S1 struct {
msg string
}
type S2 struct {
msg2 string
}
serviceDep := NewDependency(&testServiceImpl{prefix: "1"})
d1 := NewDependency(func(t testService) S1 {
return S1{t.Say("2")}
}, serviceDep)
if !d1.Static {
t.Fatalf("d1 dependency should be static: %#+v", d1)
}
d2 := NewDependency(func(t testService, s S1) S2 {
return S2{"3"}
}, serviceDep, d1)
if !d2.Static {
t.Fatalf("d2 dependency should be static: %#+v", d2)
}
}