配置并向MEF / PRISM应用程序中的所有模块公开单例

时间:2010-08-03 14:42:55

标签: c# prism mef

我有一个使用MEF和PRISM的应用程序(只是一个测试)。

加载一些符合特定接口的导出非常容易 并将它们传递给正在加载的模块的构造函数,但我正在尝试做一些不同的事情。

当应用程序启动时,它会导入IControllerClient的实现。 然后需要配置创建的实例(例如,通过shell) 应用程序中的每个模块都应该可以访问它。

我不想在Shell上有一个公共属性或暴露的一些帮助类 这个例子可能被认为是一种不好的做法......我真的不喜欢它。

更新: 改述下面的问题

我们在现有框架中定义了许多接口, 通常使用MEF将它们加载到各种应用中。

我能够将它们加载到prism应用程序的模块中,例如:

[ImportingConstructorAttribute()]
public HelloWorldView(IDataTransportService dataTransportService,
                      IMessageFactory messageFactory,
                      IDataFactory dataFactory,
                      IDataProcessor dataProcessor,
                      IDataCollector dataCollector)
{
        var client = new ControllerClient(dataTransportService,
                                          messageFactory,
                                          dataProcessor
                                          dataCollector);
}

在这种情况下,模块会创建一个有效的ControllerClient类实例。

但是我没有将这些接口传递给构造函数,而是希望有一个模块 像这样的构造函数:

[ImportingConstructorAttribute()]
public HelloWorldView(IClient client)
{
   this.client = client;
}

IClient实现的构造函数(ControllerClient)具有 [ImportingConstructorAttribute()]所以我期望注入依赖性 此时自动...但是使用此代码,甚至永远不会到达构造函数。

我想要的是拥有一个IClient接口的实例 应用程序中的所有模块。 (我现在明白,共享是MEF导入的默认值。)

最好的方法是什么?为什么我不能使用IClient的模块构造函数, 如果我不想了解mef的话,我想以这种方式公开一个类的实例呢?

所以在mef / prism app中,你在哪里定义这个可以被所有模块使用的实例?这通常被称为服务(但我只能找到关于使用统一/棱镜来暴露服务的指导)。

我希望这次我能更好地解释我的问题。

更新2: 由于默认是为MEF导入共享的,我可以在每个模块中导入IClient实现,但是我需要弄清楚为什么没有注入依赖项

1 个答案:

答案 0 :(得分:2)

对于MEF,Shared是默认值,因此每次导入界面都将解析为同一个实例。该实例的配置可以在类的构造函数中进行,或者您可以在“单例”服务类上实现IPartImportsSatisfiedNotification,这将在MEF完成解析类导入时回调。


阅读更新后的描述,听起来您无法在其构造函数中配置类,或者在解析其Imports之后,因为您需要一些额外的上下文信息。如果是这种情况,您可以在Shell中手动配置类,并在使用容器的ComposeParts方法创建导出后手动添加。这将使您的“已配置”实例成为用于解析您已应用于该类的任何[Export]标记的实例。当然,在通过依赖于实例的容器构造其他任何东西之前,你必须这样做。