2015-01-28 2 views
3

Я использую MEF, WebAPI в VS 2012.Ошибка при помощи WebAPI и MEF: Убедитесь, что контроллер имеет открытый конструктор без параметров

Я получаю ошибку

«exceptionMessage»: "Произошла ошибка при пытаясь создать контроллер типа «ClienteController» Убедитесь, что контроллер имеет публичный без параметров конструктор «» ExceptionType.. «:» System.InvalidOperationException»

I ч пр в Global.asax.cs:

public class WebApiApplication : System.Web.HttpApplication 
{ 
    protected void Application_Start() 
    { 
     AreaRegistration.RegisterAllAreas(); 
     GlobalConfiguration.Configure(WebApiConfig.Register); 
     FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters); 
     RouteConfig.RegisterRoutes(RouteTable.Routes); 
     BundleConfig.RegisterBundles(BundleTable.Bundles); 

     AggregateCatalog catalog = new AggregateCatalog(); 
     catalog.Catalogs.Add(new AssemblyCatalog(Assembly.GetExecutingAssembly())); 
     CompositionContainer container = MEFLoader.Init(catalog.Catalogs); 
     DependencyResolver.SetResolver(new MefDependencyResolver(container)); // view controllers 
     GlobalConfiguration.Configuration.DependencyResolver = new MefAPIDependencyResolver(container); // web api controllers 

    } 

В моем MEFLoader классе

public static CompositionContainer Init(ICollection<ComposablePartCatalog> catalogParts) 
    { 
     var catalog = new AggregateCatalog(); 

     catalog.Catalogs.Add(new AssemblyCatalog(typeof(BuscadorClient).Assembly)); 
     catalog.Catalogs.Add(new AssemblyCatalog(typeof(Core.DataRepositoryFactory).Assembly)); 
     catalog.Catalogs.Add(new AssemblyCatalog(typeof(Comun.DataContract.BusinessFault).Assembly)); 

     if (catalogParts != null) 
      foreach (var part in catalogParts) 
       catalog.Catalogs.Add(part); 

     var container = new CompositionContainer(catalog); 
     return container; 
    } 

Ассамблей имеет в бункерном папке веб-сайта для WebAPI применения в среде интеграции.

Примечания:

В среде разработки, Dev местные, иногда не удалось, и раствор "перекомпилировать" App Project WebAPI (csproj)

В любом случае, в среде интеграции не удалось.

Microsoft.Internal.Collections.WeakReferenceCollection 1.<CleanupDeadReferences>b__0(WeakReference w)\r\n at System.Collections.Generic.List 1.RemoveAll (предикат 1 match)\r\n at Microsoft.Internal.Collections.WeakReferenceCollection 1.Add (Т элемент) \ г \ п на System.ComponentModel.Composition.Hosting.ImportEngine.StartSatisfyingImports (PartManager partManager, AtomicComposition atomicComposition) \ r \ n в System.ComponentModel.Composition.Hosting.ImportEngine.TrySatisfyImports (PartManager partManager, ComposablePart part, Boolean shouldTrackImports) \ r \ n в System.ComponentModel.Composition.Hosting.ImportEngine.SatisfyImports (ComposablePart part) \ r \ n в System.ComponentModel.Composition.Hosting.CompositionServices.GetExportedValueFromComposedPart (движок ImportEngine, часть ComposablePart, определение ExportDefinition) \ r \ n в System.ComponentModel.Composition.Hosting.CatalogExportProvider.GetExportedValue (часть каталожной части, ExportDefinition export, Boolean isSharedPart) \ r \ n в System.ComponentModel.Composition.Primitives.Export.get_Value() \ r \ n в System.ComponentModel.Composition.ReflectionModel.ImportingItem.CastSingleExportToImportType (тип типа, экспорт экспорта) \ r \ n в System.ComponentModel.Composition.ReflectionModel.ReflectionComposablePart.SetImport (ImportingItem item, Export [] export) \ r \ n в System.ComponentModel.Composition.ReflectionModel.ReflectionComposablePart.SetImport (определение ImportDefinition, IEnumerable 1 exports)\r\n at System.ComponentModel.Composition.Hosting.ImportEngine.PartManager.TrySetImport(ImportDefinition import, Export[] exports)\r\n at System.ComponentModel.Composition.Hosting.ImportEngine.TrySatisfyImportSubset(PartManager partManager, IEnumerable 1 импорт, AtomicComposition atomicComposition) \ r \ n в System.ComponentModel.Composition.Hosting.ImportEngine.TrySatisfyImportsStateMachine (PartManager partManager, ComposablePart часть) \ r \ n в System.ComponentModel.Composition.Hosting.ImportEngine.TrySatisfyImports (PartManager partManager, ComposablePart part, Boolean shouldTrackImports) \ r \ n в System.ComponentModel.Composition.Hosting.ImportEngine.SatisfyImports (ComposablePart part) \ r \ n в System.ComponentMo del.Composition.Hosting.CompositionServices.GetExportedValueFromComposedPart (механизм ImportEngine, часть ComposablePart, определение ExportDefinition) \ r \ n в System.ComponentModel.Composition.Hosting.CatalogExportProvider.GetExportedValue (часть каталожной части, экспорт ExportDefinition, Boolean isSharedPart) \ r \ n на System.ComponentModel.Composition.Primitives.Export.get_Value() \ г \ п на COMPANY..Core.MefExtensions.GetExportedValueByType (CompositionContainer контейнера, тип типа)

+1

Может быть проблема с ** многопоточности ** – Kiquenet

+0

Я предлагаю маркировки ответ на YifanLu как правильно. MEF будет необъяснимо barf при использовании с контроллерами ASP.NET, и единственным ключом является очистка WeakReferenceCollection. Контейнер * должен быть создан как потокобезопасный. – tomo

ответ

6

Не уверен, что если кто-то по-прежнему заинтересован в ответ , но я столкнулся с той же проблемой в моем сервисе WebApi, который использует MEF в качестве IoC. Контейнер состава создается во время запуска со списком настраиваемых поставщиков экспорта.

Причина моей проблемы заключается в том, что поставщики экспорта не создаются с использованием thread safe constructor.

В этом случае, помимо установки параметра безопасности потока при создании CompositionContainer, вы также должны создать все настроенные поставщики экспорта, используя конструктор, который устанавливает значение thread safe, чтобы быть правдой.

var aggregate = new AggregateCatalog(assemblyCatalogs); 
//create default export provider to be thread safe 
var defaultExportProvider = new CatalogExportProvider(aggregate, true); 
_compContainer = new CompositionContainer(CompositionOptions.DisableSilentRejection|CompositionOptions.IsThreadSafe, defaultExportProvider); 
defaultExportProvider.SourceProvider = _compContainer; 
+0

Конечно, меня интересует ответ (отсюда и возвышение). Использование WPF (Prism) и MEF и многопоточность и получалось странное поведение. Этот самородок, реализованный в загрузчике, заставил все это уйти. Благодарю. –

Смежные вопросы

 Смежные вопросы