Скрипты IronRuby на C #: вызов метода / функции класса

Я пытаюсь использовать IronRuby для простых сценариев в приложении C #. Я пытаюсь вызвать метод класса «выполнить» для класса «Сценарий» через механизм сценариев, но он просто не работает. Я пробовал несколько методов, но, похоже, ни один из них не вызывает их.

Это мой тестовый код Ruby:

class Script
    def execute(input, parameter)
        return "test"
    end
end

Теперь я сначала хочу проверить, существует ли класс Script, есть ли у него метод execute и принимает ли этот метод ровно два параметра. Кажется, это нормально работает:

var engine = IronRuby.Ruby.CreateEngine();
var scope = engine.CreateScope();
var src = engine.CreateScriptSourceFromString(sourceCodeString, SourceCodeKind.Statements);
var compiled = src.Compile();
compiled.Execute(scope);

object rubyClass;
if (engine.Runtime.Globals.TryGetVariable("Script", out rubyClass))
{
    RubyClass instance = engine.Runtime.Globals.GetVariable("Script");

    var method = instance.GetMethod("execute");
    var param = method.GetRubyParameterArray();

    if (param.Count == 2)
    {
        // OK, try to execute (see below)
    }
}

Это будет продолжаться только в том случае, если класс и метод присутствуют с двумя параметрами, отлично.

Теперь, чтобы выполнить этот метод, я нашел три возможных способа, ни один из них не работает!

(1) Используйте dynamic, чтобы создать экземпляр класса Script и вызвать метод. Источник: Вызов IronRuby из C # с делегатом

dynamic ruby = engine.Runtime.Globals;
dynamic script = ruby.Script.@new();
return script.execute("a", "b");

При выполнении второй строки возникает следующее исключение: Метод не найден: 'Microsoft.Scripting.Actions.Calls.OverloadInfo [] Microsoft.Scripting.Actions.Calls.ReflectionOverloadInfo.CreateArray (System.Reflection.MemberInfo []) '.

(2) Использование engine.Operations.CreateInstance и динамическое:

object rubyClass = engine.Runtime.Globals.GetVariable("Script");
dynamic instance = engine.Operations.CreateInstance(rubyClass);
return instance.execute("a", "b");

Результат - то же исключение, что и (1) во второй строке.

(3) Использование engine.Operations.Invoke:

return engine.Operations.Invoke(rubyClass, "execute", "a", "b")

Другое исключение: неопределенный метод выполнения для скрипта: класс

Я в растерянности. Эта последняя попытка (3) очень похожа (если не совсем то же) на то, что я использую для Iron Python, где она отлично работает.

Есть ли проблема с моим кодом Ruby? Я не так хорошо знаком с Ruby, но этот простой тестовый класс наверняка не должен создавать никаких проблем?


person Nick Thissen    schedule 02.01.2017    source источник
comment
Возможный дубликат ошибки IronRuby: Microsoft.Scripting. Actions.Calls.OverloadInfo (пытается перенести MEF)   -  person David Cram    schedule 05.05.2017


Ответы (1)


Я сам нашел ответ здесь.

Мне нужно было добавить следующее перед моим скриптом Ruby:

class System::Object
  def initialize
  end
end
person Nick Thissen    schedule 03.01.2017