如何列出使用MEF2实现接口的所有类型?

问题描述 投票:1回答:1

[当我调用CompositionHost.GetExport<IInterface>("typename")时,我得到了所请求类型的实例,该实例实现了IInterface,一切都很好。

[当我调用CompositionHost.GetExports<IInterface>()时,我期望得到实现IInterface的所有类型的列表,但结果是一个空集合。

或者我误解了GetExports()的目的,或者我实施了错误的内容。

我的约定构建如下:

conventions.ForTypesDerivedFrom<IInterface>()
           .Export<IInterface>(builder => builder.AsContractName(type => type.Name));

我的类型是在没有属性的情况下实现的,只是在实现IInterface

是否可以使用以这种方式配置的MEF2列出类型?还是我需要更改某些东西才能实现此目的?

c# mef
1个回答
1
投票
导出合同是一种类型,或者是带有合同名称的类型。通过使用ExportBuilder.AsContractName方法,您可以明确指定合同名称。因此,您只能按其类型

和合同名称导入这些零件。

您的第一个选择是:不指定合同名称。

conventions.ForTypesDerivedFrom<IInterface>().Export<IInterface>();

然后,GetExports<IInterface>()将返回该合同类型的所有实例。但是,您将无法通过GetExport<IInterface>()导入单个实例,因为容器将引发由多个已知实现引起的异常。

顺便说一句,容器总是返回实例。您写的是期望的类型列表,但是只能从容器中获取实例(实例化零件)列表。要获取类型列表,您需要一个用于管理零件的目录。根据您的环境,您可能无法访问目录。

如果您仍然想同​​时拥有两个功能(多个实现和单个实现访问权限,请考虑从合同名称切换为元数据。

conventions .ForTypesDerivedFrom<IInterface>() .Export<IInterface>(builder => builder .AsContractType<IInterface>() .AddMetadata("ImplementationName", type => type.Name)); var myInstance = container .GetExports<Lazy<IInterface, IDictionary<string, object>>>() .Where(v => v.Metadata["ImplementationName"] == "YourImplType") .FirstOrDefault()? .Value;

[IDictionary<string, object>是通用元数据视图,允许您访问零件元数据。

© www.soinside.com 2019 - 2024. All rights reserved.