使用MEF导入由IronPython或其他DLR语言导出的组件?

时间:2012-11-12 01:30:07

标签: mef ironpython

是否可以将IronPython类声明为“Export”,从而将它们添加到MEF目录中 主机C#应用程序可以导入吗?

我无法找到任何具体的例子,只是推测。

以下是我手动加载实现.NET接口的Python类的方法:

https://github.com/versionone/VersionOne.SDK.Experimental

我希望能够在python类上放置类似于在C#中执行它的方式。 (或类似的东西)

有没有人试过这个?

谢谢, 约什

1 个答案:

答案 0 :(得分:6)

对于那些感兴趣的人,我在GitHub上发现了一个已完成此项目的项目,但有点与项目有关。经过作者的批准,我为它创建了一个新的仓库IronPythonMefNuGet package

GitHub还有其他讨论in this thread

以下是其工作原理的示例:

首先,在C#中声明的接口:

namespace IronPythonMef.Tests.Example.Operations
{
    public interface IOperation
    {
        object Execute(params object[] args);
        string Name { get; }
        string Usage { get; }
    }
}

在C#中导出该界面的实现:

[Export(typeof(IOperation))]
public class Power : IOperation
{
    public object Execute(params object[] args)
    {
        if (args.Length < 2)
        {
            throw new ArgumentException(Usage, "args");
        }

        var x = Convert.ToDouble(args[0]);
        var y = Convert.ToDouble(args[1]);

        return Math.Pow(x, y);
    }

    public string Name
    {
        get { return "pow"; }
    }

    public string Usage
    {
        get { return "pow n, y -- calculates n to the y power"; }
    }
}

并且,IronPython中的IOperation实现:

@export(IOperation)
class Fibonacci(IOperation):
    def Execute(self, n):
        n = int(n)
        if n == 0:
            return 0
        elif n == 1:
            return 1
        else:
            return self.Execute(n-1) + self.Execute(n-2)

    @property
    def Name(self):
        return "fib"

    @property
    def Usage(self):
        return "fib n -- calculates the nth Fibonacci number"

这是一个类的测试用例,它从C#和IronPython导入这些操作并执行它们:

[TestFixture]
public class MathWizardTests
{
    [Test]
    public void runs_script_with_operations_from_both_csharp_and_python()
    {
        var mathWiz = new MathWizard();

        new CompositionHelper().ComposeWithTypesExportedFromPythonAndCSharp(
            mathWiz,
            "Operations.Python.py",
            typeof(IOperation));

        const string mathScript =
@"fib 6
fac 6
abs -99
pow 2 4
";
        var results = mathWiz.ExecuteScript(mathScript).ToList();

        Assert.AreEqual(8, results[0]);
        Assert.AreEqual(720, results[1]);
        Assert.AreEqual(99f, results[2]);
        Assert.AreEqual(16m, results[3]);
    }
}