impworks / lens

Language for Embeddable .NET Scripting
MIT License
91 stars 9 forks source link

LE3063: Only public, static, non-generic methods can be imported! #188

Closed ForNeVeR closed 7 years ago

ForNeVeR commented 7 years ago

With this restriction, it's almost impossible to import F# function. See my example program below:

open System
open Lens

// little hack from https://stackoverflow.com/a/1575450/2684760
let getMethodInfo (f : 'a -> 'b) = (FSharpFunc.ToConverter f).Method

[<EntryPoint>]
let main argv = 
    let cp = new LensCompiler()
    let foo = fun x -> x + 5
    let res = ref 0
    let mi = getMethodInfo foo
    printfn "isPublic = %A; isStatic = %A, isGeneric = %A" mi.IsPublic mi.IsStatic mi.IsGenericMethod
        // => isPublic = false; isStatic = false, isGeneric = false
    cp.RegisterFunction("foo", mi)
    cp.RegisterProperty("res", fun () -> res.Value, fun v -> res := v)
    let src = "res = foo 10"
    let compiled = cp.Compile src

    0

I suggest to review that restriction if that's possible for us.

impworks commented 7 years ago

Поскольку лямбда является инстанс-методом, ее нужно передавать через RegisterProperty. Но есть бага: переданный таким образом делегат нельзя вызвать напрямую из-за ошибки в InvocationNode. Это нужно исправить!

impworks commented 7 years ago

Сейчас не могу исправить - сначала нужно доделать #187, иначе будут конфликты. В качестве временного решения, можно использовать явный вызов Invoke:

Func<int, int> foo = x => x + 5;
cp.RegisterProperty("foo", () => foo);
cp.Run("foo.Invoke 10"); // 15

В будущем, можно добавить overload RegisterFunction(Delegate d), чтобы было более наглядно.

ForNeVeR commented 7 years ago

RegisterProperty подойдёт только для функции без параметров. А что делать, если у меня параметры? Можно, конечно, как-то извернуться на Property (скажем, через несколько пропертей выставлять параметры, а ещё через одну — вызывать функцию), но это кошмар.

Ок, понял. Да, это возможно.

impworks commented 7 years ago

Бага исправлена, интерфейс компилятора расширен.