MEF DirectoryCatalog читает одну и ту же DLL много раз
У меня была простая реализация MEF, загружающая некоторые dll (плагины) из каталога. Это работало хорошо под MEF1, но теперь я хочу использовать ту же функциональность с MEF2, и это дает мне IEnumerable, который содержит правильное количество dll, которые находятся в каталоге, но все сборки одинаковы.
Например, у меня есть две сборки: fakeplugin1.dll и fakeplugin2.dll в каталоге. Они экспортируют классы FakePlugin1 и FakePlugin2. Теперь, когда я вызываю container.ComposeParts(), у меня нет ничего в списке, украшенном ImportMany и container.Catalog, содержит две сборки в каталоге, но обе они являются FakePlugin1.
Вот код:
[ImportMany(typeof (IDCPlugin))]
IEnumerable<IDCPlugin> workplaceControllers;
var catalog = new DirectoryCatalog(AppDomain.CurrentDomain.BaseDirectory);
var agcatalogue = new AggregateCatalog(catalog);
var container = new CompositionContainer(agcatalogue);
container.ComposeParts();
Я пытаюсь использовать ExportFactory и RegistrationBuilder, но я только что понял, что даже базовая функциональность не работает должным образом.
Что я делаю неправильно? Что-то изменилось в MEF2, я должен знать? Как загрузить две разные сборки?:)
Заранее спасибо за помощь!
Редактировать: всегда создает два экземпляра первого типа в папке (по возрастанию в abc). Если я положу другой в папку, он создаст три одинаковых и т. Д.
Изменить: я загрузил код в pastebin, который дает тот же результат с MEF2: http://pastebin.com/3fWcujPS
1 ответ
Каталог будет содержать определения импорта и экспорта для всего обнаруженного. Независимо от того, действительно ли вам это нужно.
Это "особенность" MEF. Вам нужно будет либо ImportMany
и выборочно фильтровать плагины, которые вам нужны.
Итак, как вы изящно обрабатываете несколько плагинов? Попробуй это:
[Export]
public class PluginService
{
public const string BEST_PLUGIN = "BestPlugin";
[ImportMany]
public IEnumerable<Plugin> Plugins{ private get; set; }
[Export(BEST_PLUGIN)]
public Plugin BestPlugin{ get { return GetBestPlugin(); } }
Plugin GetBestPlugin()
{
return Plugins.FirstOrDefault(); //or some other logic for selection
}
}
Если ваши плагины ресурсоемки, вы можете рассмотреть возможность отложенной инициализации.
Lazy<T, TMetadata>
это тип, предоставленный MEF для хранения косвенных ссылок на экспорт. Здесь, в дополнение к самому экспортированному объекту, вы также получаете метаданные экспорта или информацию, которая описывает экспортируемый объект. каждыйLazy<T, TMetadata>
содержитIOperation
объект, представляющий фактическую операцию, иIOperationData
объект, представляющий его метаданные.
http://msdn.microsoft.com/en-us/library/dd460648.aspx
MEF имеет строгие правила по количеству компонентов (количество вещей), чтобы гарантировать, что не будет никаких сюрпризов, но это означает, что вы должны быть осторожны с развертыванием.