Beispiel #1
0
func ExampleGRPChw() {
	go servermain()
	time.Sleep(time.Second)

	l, nerr := glick.New(nil)
	if nerr != nil {
		log.Fatal(nerr)
	}
	var req pb.HelloRequest
	var err error
	if err = l.RegAPI("hw", &req, func() interface{} { var hr pb.HelloReply; return interface{}(&hr) }, 2*time.Second); err != nil {
		log.Fatal(err)
	}
	if err = ConfigGRPChw(l); err != nil {
		log.Fatal(err)
	}
	if err = l.Configure([]byte(`[
{"Plugin":"ExampleGRPChw","API":"hw","Actions":["hwAct"],"Type":"gRPChw","Path":"` + address + `"}
		]`)); err != nil {
		log.Fatal(err)
	}
	req.Name = "gRPC"
	ctx, cancelCtx := context.WithTimeout(context.Background(), time.Second)
	defer cancelCtx()
	var repI interface{}
	repI, err = l.Run(ctx, "hw", "hwAct", &req)
	if err != nil {
		log.Fatal(err)
	}
	fmt.Println(repI.(*pb.HelloReply).Message)
	// output: Hello gRPC
}
Beispiel #2
0
func TestOverloaderForever(t *testing.T) {
	l, nerr := glick.New(func(ctx context.Context, api, act string, handler glick.Plugin) (context.Context, glick.Plugin, error) {
		return ctx, nil, nil
	})
	if nerr != nil {
		t.Error(nerr)
	}
	var prototype int
	if err := l.RegAPI("abc", prototype,
		func() interface{} { var b bool; return interface{}(&b) },
		time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("abc", "forever", Forever, nil); err != nil {
		t.Error(err)
		return
	}
	ctx, can := context.WithTimeout(context.Background(), time.Millisecond)
	defer can()
	if _, err := l.Run(ctx, "abc", "forever", 1); err == nil {
		t.Error("overloader should have errored")
		return
	}
}
Beispiel #3
0
func TestGetURL(t *testing.T) {
	outProtoString := func() interface{} { var s string; return interface{}(&s) }
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}
	proto := ""
	if err := l.RegAPI("string/*string", proto, outProtoString, 2*time.Second); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("string/*string", "bad1",
		glick.PluginGetURL(true, "", &proto), nil); err == nil {
		t.Error("empty url not errored")
	}
	if err := l.RegPlugin("string/*string", "dynamic1",
		glick.PluginGetURL(false, "", &proto), nil); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("string/*string", "documize",
		glick.PluginGetURL(true, "https://documize.com", &proto), nil); err != nil {
		t.Error(err)
	}
	if _, err := l.Run(nil, "string/*string", "documize", ""); err != nil {
		t.Error(err)
	}
	if _, err := l.Run(nil, "string/*string", "dynamic1", "http://golang.org"); err != nil {
		t.Error(err)
	}
	if _, err := l.Run(nil, "string/*string", "dynamic1", ""); err == nil {
		t.Error("empty url did not error")
	}
	if _, err := l.Run(nil, "string/*string", "dynamic1", "!@£$%^&*()"); err == nil {
		t.Error("bad url did not error")
	}
}
Beispiel #4
0
func TestBadInterface(t *testing.T) {
	l, errN := glick.New(nil)
	if errN != nil {
		t.Error(errN)
	}
	var proto string
	var ip int
	ipProto := func() interface{} { var i int; return interface{}(&i) }
	if err := l.RegAPI("int/&int", ip, ipProto, 3*time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("int/&int", "pwd",
		glick.PluginCmd([]string{"pwd"}, &proto), nil); err != nil {
		t.Error(err)
		return
	}
	if _, err := l.Run(nil, "int/&int", "pwd", 11); err == nil {
		t.Error("does not error on non string input value")
		return
	}
	if err := l.RegAPI("string/&int", proto, ipProto, 3*time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("string/&int", "pwd",
		glick.PluginCmd([]string{"pwd"}, &proto), nil); err != nil {
		t.Error(err)
		return
	}
	if _, err := l.Run(nil, "string/&int", "pwd", "foo"); err == nil {
		t.Error("does not error on non *string ouput value")
		return
	}
}
Beispiel #5
0
func pieSwitchTest(t *testing.T, useJSON bool) {
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
		return
	}
	if err := glpie.ConfigPIE(l); err != nil {
		t.Error(err)
		return
	}
	var proto string
	protoOut := func() interface{} {
		s := ""
		return interface{}(&s)
	}
	if err := l.RegAPI("string/&string", proto, protoOut, 10*time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("string/&string", "cmdBad",
		glpie.PluginPie(useJSON, "dingbat", []string{"doodah"}, protoOut), nil); err == nil {
		t.Error("garbage pie plugin did not fail")
		return
	}
	if _, err := l.Run(nil, "string/&string", "cmdBad", proto); err == nil {
		t.Error("bad command did not fail")
		return
	}
	api := fmt.Sprintf("API%v", useJSON)
	act := fmt.Sprintf("ACT%v", useJSON)
	tisOut := func() interface{} {
		return interface{}(&test.IntStr{})
	}
	if err := l.RegAPI(api, test.IntStr{}, tisOut, 2*time.Second); err != nil {
		t.Error(err)
		return
	}
	cmdPath := "./_test/gob/gob"
	if useJSON {
		cmdPath = "./_test/json/json"
	}
	if err := l.RegPlugin(api, act,
		glpie.PluginPie(useJSON, "CI.CopyIntX", []string{cmdPath}, tisOut), nil); err != nil {
		t.Error("unable to create " + err.Error())
		return
	}

	parTest(t, l, api, act, cmdPath, useJSON, tisOut)

}
Beispiel #6
0
func servermain() {
	lib, nerr := glick.New(nil)
	if nerr != nil {
		panic(nerr)
	}
	if err := lib.RegAPI("api", uppercaseRequest{},
		func() interface{} { return uppercaseResponse{} }, time.Second); err != nil {
		panic(err)
	}
	if err := lib.RegPlugin("api", "lc",
		func(ctx context.Context, in interface{}) (interface{}, error) {
			return uppercaseResponse{
				V: strings.ToLower(in.(uppercaseRequest).S),
			}, nil
		}, nil); err != nil {
		panic(err)
	}

	ctx := context.Background()
	svc := stringService{}

	lowercaseHandler := httptransport.NewServer(
		ctx,
		glkit.MakeEndpoint(lib, "api", "lc"),
		decodeUppercaseRequest,
		encodeResponse,
	)

	uppercaseHandler := httptransport.NewServer(
		ctx,
		makeUppercaseEndpoint(svc),
		decodeUppercaseRequest,
		encodeResponse,
	)

	countHandler := httptransport.NewServer(
		ctx,
		makeCountEndpoint(svc),
		decodeCountRequest,
		encodeResponse,
	)

	http.Handle("/uppercase", uppercaseHandler)
	http.Handle("/lowercase", lowercaseHandler)
	http.Handle("/count", countHandler)
	log.Fatal(http.ListenAndServe("localhost:8080", nil))
}
Beispiel #7
0
func client(t *testing.T, useJSON bool, tisOut func() interface{}, endPt string) {

	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}

	api := "ab"
	act := "cdef"
	if err := l.RegAPI(api, test.IntStr{}, tisOut, 2*time.Second); err != nil {
		t.Error(err)
		return
	}

	if err := l.RegPlugin(api, act,
		glick.PluginRPC(useJSON, "CI.CopyIntX", endPt, tisOut), nil); err != nil {
		t.Error("unable to create JsonRPC " + err.Error())
		return
	}

	par := test.IntStr{I: 42}
	if ret, err := l.Run(nil, api, act, par); err != nil {
		t.Error("unable to run plugin " + err.Error())
	} else {
		if ret.(*test.IntStr).I != 42 {
			t.Error("RPC integer copy did not work")
		}
	}
	par.I = 4
	if _, err := l.Run(nil, api, act, par); err == nil {
		t.Error("over-long plugin did not timeout")
	}

	if err := l.RegPlugin(api, "bep",
		glick.PluginRPC(useJSON, "", "localhost:8080", tisOut), nil); err == nil {
		t.Error("able to create empty end-point method")
		return
	}

	if err := l.RegPlugin(api, "bep",
		glick.PluginRPC(useJSON, "CI.CopyIntX", "", tisOut), nil); err == nil {
		t.Error("able to create empty endpoint")
		return
	}
}
Beispiel #8
0
func TestGoKitStringsvc1(t *testing.T) {
	go servermain()

	<-time.After(2 * time.Second)

	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}

	if err := glkit.ConfigKit(l); err != nil {
		t.Error(err)
	}
	if err := l.RegAPI("uppercase", uppercaseRequest{},
		func() interface{} { return &uppercaseResponse{} }, time.Second); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"gk","API":"uppercase","Actions":["uc"],"Type":"KIT","Path":"http://localhost:8080/uppercase","JSON":true},
{"Plugin":"gk","API":"uppercase","Actions":["lc"],"Type":"KIT","Path":"http://localhost:8080/lowercase","JSON":true}
		]`)); err != nil {
		t.Error(err)
	}
	if rep, err := l.Run(nil, "uppercase", "uc", uppercaseRequest{S: "abc"}); err == nil {
		if rep.(*uppercaseResponse).V != "ABC" {
			t.Error("uppercase did not work")
		}
	} else {
		t.Error(err)
	}
	if rep, err := l.Run(nil, "uppercase", "lc", uppercaseRequest{S: "XYZ"}); err == nil {
		if rep.(*uppercaseResponse).V != "xyz" {
			t.Error("lowercase did not work")
		}
	} else {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"gk","API":"uppercase","Actions":["uc"],"Type":"KIT","Path":"http://localhost:8080/uppercase","Gob":true}
		]`)); err == nil {
		t.Error("did not spot non-JSON")
	}

	testCount(t)
}
Beispiel #9
0
func TestTimeout(t *testing.T) {
	l, errN := glick.New(nil)
	if errN != nil {
		t.Error(errN)
	}
	var proto string
	outProto := func() interface{} { var s string; return interface{}(&s) }
	if err := l.RegAPI("alwaysTimeout", proto, outProto, 1*time.Second); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("alwaysTimeout", "sleep",
		glick.PluginCmd([]string{"sleep", "10"}, &proto), nil); err != nil {
		t.Error(err)
		return
	}
	if _, err := l.Run(nil, "alwaysTimeout", "sleep", "foo"); err == nil {
		t.Error("does not timeout when it should")
	}
}
Beispiel #10
0
func TestDup(t *testing.T) {
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}
	var d struct{}
	if er0 := l.RegAPI("A", d,
		func() interface{} { var s struct{}; return interface{}(&s) },
		time.Second); er0 != nil {
		t.Error("register API gives error")
	}
	if er1 := l.RegPlugin("A", "B", Simp, nil); er1 != nil {
		t.Error("first entry gives error")
	}
	er2 := l.RegPlugin("A", "B", Simp, nil)
	if er2 != nil {
		t.Error("second entry should not give error")
	}
}
Beispiel #11
0
func TestCmd(t *testing.T) {
	l, errN := glick.New(nil)
	if errN != nil {
		t.Error(errN)
	}
	var proto string
	outProto := func() interface{} { var s string; return interface{}(&s) }
	if err := l.RegAPI("string/&string", proto, outProto, 10*time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("string/&string", "pwdBad",
		glick.PluginCmd([]string{"pwdBad"}, &proto), nil); err == nil {
		t.Error("incorrect cmd plugin did not fail")
		return
	}
	if _, err := l.Run(nil, "string/&string", "pwdBad", proto); err == nil {
		t.Error("bad simple command did not fail")
		return
	}
	if err := l.RegPlugin("string/&string", "pwd",
		glick.PluginCmd([]string{"pwd"}, &proto), nil); err != nil {
		t.Error(err)
		return
	}
	if proto, err := l.Run(nil, "string/&string", "pwd", proto); err != nil {
		t.Error(err)
	} else {
		p := *proto.(*string)
		if !strings.HasSuffix(p, "/glick\n") {
			t.Error("wrong output from pwd: " + p)
		}
	}
	if err := l.RegPlugin("string/&string", "exit1",
		glick.PluginCmd([]string{"bash", "./_test/exit1.sh"}, &proto), nil); err != nil {
		t.Error(err)
		return
	}
	if _, err := l.Run(nil, "string/&string", "exit1", proto); err == nil {
		t.Error("exit1.sh does not give an error")
	}
}
Beispiel #12
0
func clientBad(t *testing.T, useJSON bool, tisOut func() interface{}, endPt string) {

	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}

	api := "ab"
	act := "cdef"
	if err := l.RegAPI(api, test.IntStr{}, tisOut, 2*time.Second); err != nil {
		t.Error(err)
		return
	}

	if err := l.RegPlugin(api, act,
		glick.PluginRPC(useJSON, "CI.CopyIntX", endPt, tisOut), nil); err != nil {
		t.Error("unable to create JsonRPC " + err.Error())
		return
	}

	par := test.IntStr{I: 42}

	if err := l.RegPlugin(api, "errEP",
		glick.PluginRPC(useJSON, "CI.CopyIntX", "localhost:9999", tisOut), nil); err != nil {
		t.Error("error on valid (if unused) endpoint")
		return
	}
	if _, err := l.Run(nil, api, "errEP", par); err == nil {
		t.Error("did not error on unpopulated end-point")
	}

	noPoint := func() interface{} { return interface{}(42) }
	if err := l.RegAPI("noPoint", 42, noPoint, 0); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("noPoint", "errEP",
		glick.PluginRPC(useJSON, "CI.CopyIntX", "localhost:9999", noPoint), nil); err == nil {
		t.Error("a non-pointer return should error")
	}

}
Beispiel #13
0
func TestConfig2(t *testing.T) {
	l, ne := glick.New(nil)
	if ne != nil {
		t.Error(ne)
	}
	protoString := ""
	outProtoString := func() interface{} { var s string; return interface{}(&s) }
	outProtoInt := func() interface{} { var i int; return interface{}(&i) }

	if err := l.RegAPI("string/*string", protoString, outProtoString, 0); err != nil {
		t.Error(err)
	}
	var is test.IntStr
	if err := l.RegAPI("test", is, outProtoInt, 0); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p66","API":"test","Actions":["intStr3"],"Type":"RPC","Path":"localhost:4242","Method":"foo.bar","Token":"ABC"}
		]`)); err != nil {
		t.Error(err)
	}
	if l.Token("test", "intStr3") != "ABC" {
		t.Error("Token value not set and retrieved")
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p74","API":"test","Actions":["intStr4"],"Type":"RPC","Path":"foo;;:4242"}
		]`)); err == nil {
		t.Error("unsuited endPoint not spotted")
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p79","API":"string/*string","Actions":["goodURL"],"Type":"URL","Path":"http://golang.org","Static":true}
		]`)); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p84","API":"string/*string","Actions":["badURL"],"Type":"URL","Path":"","Static":true}
		]`)); err == nil {
		t.Error("unsuited URL not spotted")
	}
}
Beispiel #14
0
func TestConfig(t *testing.T) {
	l, ne := glick.New(nil)
	if ne != nil {
		t.Error(ne)
	}
	protoString := ""
	outProtoString := func() interface{} { var s string; return interface{}(&s) }

	if err := l.RegAPI("string/*string", protoString, outProtoString, 0); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p34","API":"string/*string","Actions":["doIt"]}
		]`)); err == nil {
		t.Error("missing Type not an error")
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p39","API":"string/*string","Actions":["pwd"],"Type":"CMD","Cmd":["pwd"]}
		]`)); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p44","API":"string/*string","Actions":["garbage"],"Type":"CMD","Cmd":["garbage"]}
		]`)); err == nil {
		t.Error("garbage cmd path did not error")
	}
	if err := l.RegAPI("int/*string", 42, outProtoString, 0); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p52","API":"int/*string","Actions":["badAPI"],"Type":"CMD","Cmd":["pwd"]}
		]`)); err == nil {
		t.Error("unsuited API for cmd did not error")
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p57","API":"int/*string","Actions":["badAPI"],"Type":"URL","Path":["pwd"]}
		]`)); err == nil {
		t.Error("unsuited API for URL did not error")
	}
}
Beispiel #15
0
func TestOverloaderBad(t *testing.T) {
	l, nerr := glick.New(func(ctx context.Context, api, act string, handler glick.Plugin) (context.Context, glick.Plugin, error) {
		if api == "abc" && act == "bad" {
			return ctx, nil, errors.New("you done a bad... bad... thing")
		}
		return ctx, nil, nil
	})
	if nerr != nil {
		t.Error(nerr)
	}
	var prototype int
	if err := l.RegAPI("abc", prototype,
		func() interface{} { var b bool; return interface{}(&b) },
		time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("abc", "bad", Def, nil); err != nil {
		t.Error(err)
		return
	}
	if _, err := l.Run(nil, "abc", "bad", 1); err == nil {
		t.Error("overloader should have errored")
		return
	}
	ctx, can := context.WithTimeout(context.Background(), time.Millisecond)
	defer can()
	if err := l.RegPlugin("abc", "justBad", JustBad, nil); err != nil {
		t.Error(err)
		return
	}
	ctx, can = context.WithTimeout(context.Background(), time.Millisecond)
	defer can()
	if _, err := l.Run(ctx, "abc", "justBad", 1); err == nil {
		t.Error("overloader should have errored")
		return
	}

}
Beispiel #16
0
func TestBadConfig(t *testing.T) {
	l, ne := glick.New(nil)
	if ne != nil {
		t.Error(ne)
	}
	if err := l.Configure([]byte("±§~`-=_+")); err == nil {
		t.Error("did not error on rubbish")
	}
	if err := l.Configure([]byte("[]")); err != nil {
		t.Error(err)
	}
	if err := l.Configure([]byte(`[
{"Plugin":"p22",API":"missing"}
		]`)); err == nil {
		t.Error("missing API not an error")
	}
	if err := l.AddConfigurator("zombie", nil); err == nil {
		t.Error("nil configurator not spotted")
	}
	if err := glick.ConfigGetURL(l); err == nil {
		t.Error("duplicate configurator not spotted")
	}
}
Beispiel #17
0
func TestAPI(t *testing.T) {
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}
	if err := l.RegAPI("z", nil, nil, time.Second); err != glick.ErrNilAPI {
		t.Error("does not return nil api error")
	}
	var dummy int
	outGood := func() interface{} { var d int; return interface{}(&d) }
	if err := l.RegAPI("z", dummy, outGood, time.Second); err != nil {
		t.Error("1st reg API returns error")
	}
	if err := l.RegAPI("z", dummy, outGood, time.Second); err == nil {
		t.Error("does not return duplicate api error")
	}
	if _, err := l.Run(nil, "z", "unknown", dummy); err == nil {
		t.Error("does not return no plugin")
	}
	if _, err := l.Run(nil, "unknown", "unknown", dummy); err == nil {
		t.Error("does not return unknown api error")
	}
}
Beispiel #18
0
func TestGetURLint(t *testing.T) {
	outProtoString := func() interface{} { var s string; return interface{}(&s) }
	outProtoInt := func() interface{} { var i int; return interface{}(&i) }
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}
	proto := ""

	ip := 0
	if err := l.RegAPI("int/*string", ip, outProtoString, 2*time.Second); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("int/*string", "documize",
		glick.PluginGetURL(true, "https://documize.com", &proto), nil); err != nil {
		t.Error(err)
	}
	if _, err := l.Run(nil, "int/*string", "documize", 42); err == nil {
		t.Error("bad api in did not error")
	}
	if err := l.RegAPI("string/*int", proto, outProtoInt, 2*time.Second); err != nil {
		t.Error(err)
	}
	if err := l.RegPlugin("string/*int", "documize",
		glick.PluginGetURL(true, "https://documize.com", &proto), nil); err != nil {
		t.Error(err)
	}
	if _, err := l.Run(nil, "string/*int", "documize", ""); err == nil {
		t.Error("bad api out did not error")
	}
	if _, err := l.Run(nil, "string/*string", "documize", nil); err == nil {
		t.Error("nil input value did not error")
	}
	if _, err := l.Run(nil, "string/*string", "documize", true); err == nil {
		t.Error("incorrect input value did not error")
	}
}
Beispiel #19
0
func TestOverloaderMOL(t *testing.T) {
	hadOvStub := Tov
	l, nerr := glick.New(func(ctx context.Context, api, act string, handler glick.Plugin) (context.Context, glick.Plugin, error) {
		if api == "abc" && act == "meaning-of-life" {
			return ctx, hadOvStub, nil
		}
		return ctx, nil, nil
	})
	if nerr != nil {
		t.Error(nerr)
	}
	var prototype int
	if err := l.RegAPI("abc", prototype,
		func() interface{} { var b bool; return interface{}(&b) },
		time.Second); err != nil {
		t.Error(err)
		return
	}
	if err := l.RegPlugin("abc", "default", Def, nil); err != nil {
		t.Error(err)
		return
	}
	if ret, err := l.Run(nil, "abc", "default", 1); err != nil {
		t.Error(err)
	} else {
		if *ret.(*bool) {
			t.Error("Overloaded function called in error")
		}
	}
	if ret, err := l.Run(nil, "abc", "meaning-of-life", 1); err != nil {
		t.Error(err)
	} else {
		if !*ret.(*bool) {
			t.Error("Overloaded function not called")
		}
	}
}
Beispiel #20
0
func TestSimple(t *testing.T) {
	l, nerr := glick.New(nil)
	if nerr != nil {
		t.Error(nerr)
	}
	api := "S"
	var i int
	if err := l.RegPlugin("unknown", "Test", Simp, nil); err == nil {
		t.Error("register plugin does not give unknown API error")
	}
	if err := l.RegAPI(api, i, outSimp, time.Second); err != nil {
		t.Error(err)
		return
	}
	if er1 := l.RegPlugin(api, "Test", Simp, nil); er1 != nil {
		t.Error("register gives error", er1)
	}
	if ret, err := l.Run(nil, api, "Test", 42); err != nil {
		t.Error(err)
	} else {
		if *ret.(*int) != 42 {
			t.Error("called plugin did not work")
		}
	}

	if ppo, err := l.ProtoPlugOut(api); err == nil {
		if reflect.TypeOf(ppo()) != reflect.TypeOf(outSimp()) {
			t.Error("wrong proto type")
		}
	} else {
		t.Error(err)
	}
	if _, err := l.ProtoPlugOut("Sinbad"); err == nil {
		t.Error("no error for non-existant api")
	}
}
Beispiel #21
0
func Example() {

	goDatePlugin := func(ctx context.Context, in interface{}) (interface{}, error) {
		return time.Now().String(), nil
	}

	runtimeRerouter := func(ctx context.Context, api, action string, handler glick.Plugin) (context.Context, glick.Plugin, error) {
		// if we hit a particular set of circumstances return the go version
		if ctx.Value("bingo") != nil && api == "timeNow" && action == "lookup" {
			return ctx, goDatePlugin, nil
		}
		// otherwise return what we we were planning to do anyway
		return ctx, handler, nil
	}

	lib, nerr := glick.New(runtimeRerouter)
	if nerr != nil {
		fmt.Println(nerr)
		return
	}

	timeNowAPIproto := ""
	if err := lib.RegAPI("timeNow", timeNowAPIproto,
		func() interface{} { return timeNowAPIproto },
		time.Second); err != nil {
		fmt.Println(err)
		return
	}

	// the set-up version of the plugin, in Go
	if err := lib.RegPlugin("timeNow", "lookup", goDatePlugin, nil); err != nil {
		fmt.Println(err)
		return
	}

	ctx := context.Background()

	lookup := func() {
		if S, err := lib.Run(ctx, "timeNow", "lookup", ""); err != nil {
			fmt.Println(err)
		} else {
			fmt.Println(S)
		}
	}

	lookup() // should run the go version

	// now overload an os version of timeNow/lookup via a JSON config
	if err := lib.Configure([]byte(`[
{"Plugin":"OS-style-date","API":"timeNow","Actions":["lookup"],"Type":"CMD","Cmd":["date"]}
		]`)); err != nil {
		fmt.Println(err)
	}

	lookup() // should run the os command 'date' and print the output

	// now set a specific context to be picked-up in runtimeRerouter
	ctx = context.WithValue(ctx, "bingo", "house")

	lookup() // should run the go version again after being re-routed

}