fix: function created by reflect.MakeFunc using closure had wrong type (#75)

Call genNodeWrapper on interpreted function returned by a closure,
itself being wrapped, to ensure that the function can be called from
binary, no matter the level of nesting closures.
This commit is contained in:
Marc Vertes
2019-02-03 15:38:21 +01:00
committed by Ludovic Fernandez
parent 6fc6560af3
commit 18330ad7f9
3 changed files with 60 additions and 2 deletions

View File

@@ -0,0 +1,17 @@
package bar
import (
"fmt"
)
var version = "v1"
func NewSample() func(string, string) func(string) string {
fmt.Println("in NewSample")
return func(val string, name string) func(string) string {
fmt.Println("in function", version, val, name)
return func(msg string) string {
return fmt.Sprint("here", version, val, name, msg)
}
}
}

View File

@@ -0,0 +1,36 @@
package clos1
import (
"testing"
"github.com/containous/dyngo/interp"
"github.com/containous/dyngo/stdlib"
)
func TestFunctionCall(t *testing.T) {
i := interp.New(interp.Opt{GoPath: "./_pkg"})
i.Use(stdlib.Value, stdlib.Type)
_, err := i.Eval(`import "foo/bar"`)
if err != nil {
t.Fatal(err)
}
fnv, err := i.Eval(`bar.NewSample()`)
if err != nil {
t.Fatal(err)
}
fn, ok := fnv.Interface().(func(string, string) func(string) string)
if !ok {
t.Fatal("conversion failed")
}
fn2 := fn("hello", "world")
val := fn2("truc")
expected := "herev1helloworldtruc"
if val != expected {
t.Errorf("Got: %q, want: %q", val, expected)
}
}

View File

@@ -363,8 +363,13 @@ func genNodeWrapper(n *Node) func(*Frame) reflect.Value {
if len(def.child[2].child) > 1 {
if fieldList := def.child[2].child[1]; fieldList != nil {
result = make([]reflect.Value, len(fieldList.child))
for i := range fieldList.child {
result[i] = frame.data[i]
for i, c := range fieldList.child {
if c.typ.cat == FuncT {
gv := genNodeWrapper(frame.data[i].Interface().(*Node))
result[i] = gv(f)
} else {
result[i] = frame.data[i]
}
}
}
}