1

我试图在我定义的类中获取导出的属性,但我认为缺少一些我不知道的东西。这是我的处理程序类:

public class Handler
{
    public string Message { get; private set; }
    public void Create(string msg)
    {
        Message = msg;
    }
}

我的 HandlerUser 类是:

public class HandlerUser
{
    [Export(typeof(Handler))]
    public Handler MyHandler { get; set; }
    public string Name { get; set; }

    public HandlerUser() { MyHandler = new Handler(); }
}

在我的 program.cs 中,我有:

        var catalogs = new AggregateCatalog();
        var catalog = new ApplicationCatalog();
        catalogs.Catalogs.Add(catalog);

        CompositionContainer pluginsCompositionContainer  = new CompositionContainer(catalogs);

        HandlerUser u1 = new HandlerUser();
        u1.MyHandler.Create("U1");
        HandlerUser u2 = new HandlerUser();
        u2.MyHandler.Create("U2");

        var exports = pluginsCompositionContainer.GetExports<Handler>();
        Console.Write(exports.Count());

我希望看到 2 个出口,他们应该有 "U1","U2" 作为他们的消息,但我只看到一个,消息是空的。我不知道缺少什么,我Handler只是想导出 Every made in code,并且能够做一些逻辑。任何帮助都会很棒。

4

2 回答 2

0

使用 MEF 时,您不能导出某些类的属性或方法(作为类型),您需要导出类本身,因此您的代码应该是这样的:

    [Export(typeof(Handler))]
    public class HandlerUser : Handler
    {
        public string Name { get; set; }

        public HandlerUser() : base()
        {
        }
    }

但是由于您使用的是 MEF,这意味着您正在尝试为您的应用程序添加可扩展性,考虑到这一点,我会将“Handle”设为一个接口而不是一个类,所以这样任何人都可以实现他们想要的方式,他们只需要来实现接口。

在这种情况下,就像:

    public interface IHandler
    {
        string Message { get; }
        public void Create(string msg);

    }

    [Export(typeof(Handler))]
    public class HandlerUser : IHandler
    {
        public string Name { get; set; }
        public string Message { get; private set;}

        public HandlerUser() 
        {
        }

        public void Create(string msg)
        {
           this.Message = msg
        }
    }

编辑:

我已经更新了答案,以明确 MEF 如何与导出一起使用,您实际上可以导出属性,但不能在问题的上下文中。执行此操作时,您将通过属性名称“Handler”而不是 typeof(Handler) 进行导出,就像在类定义中所做的那样。属性和方法导出是一个很酷的功能,但有一些限制(方法导出的最大参数数量为 4 个!),尽可能使用类导出。

可以在此处找到有关使用 MEF 导出的更多信息

于 2013-05-17T21:51:08.850 回答
0

您只看到一个导出的原因是因为CompositionContainer不知道您自己创建的其他两个对象。

要让 CompositionContainer 使用另外两个Handlers,请将每个 HandleUser 传递给CompositionContainer.ComposeParts方法。这会将处理程序注册到容器中。

pluginsCompositionContainer.ComposeParts(u1);
pluginsCompositionContainer.ComposeParts(u2);

然后,当您获得导出时,您会注意到它们不是两个(如您最初预期的那样),而是三个。您自己创建并使用注册到容器的两个CompositionContainer.ComposeParts加上容器自动创建的一个(实际上是 a Lazy<Handler>)。最后一个是您在示例代码中看到的那个。当您尝试访问这个特定的导出值时,容器将创建一个实例,HandlerUser然后返回对Handler.

于 2013-08-16T14:17:50.297 回答