Search code examples
c#dependency-injectionprismmefprism-5

MEF ComposeExportedValue vs Export attribute


I am having difficulties to understand why we need ComposeExportedValue(objval) instead of just using [Export] attribute.

I hava an application object created in shell, and this application object needs to be injected to prism modules.

public class ShellBootsrapper : MefBootstrapper
{

    [Export(typeof(IMyApplication))]
    public MyApplication myApp; 

    protected override DependencyObject CreateShell()
    {
        this.Container.ComposeExportedValue<IMyApplication>(myApp);
        return this.Container.GetExportedValue<Shell>();
    }

    protected override void ConfigureAggregateCatalog()
    {
       base.ConfigureAggregateCatalog();
       myApp = new MyApplication();
       this.AggregateCatalog.Catalogs.Add(new AssemblyCatalog(System.Reflection.Assembly.GetExecutingAssembly()));
      this.AggregateCatalog.Catalogs.Add(new AssemblyCatalog(typeof(Module1.Module1).Assembly));
}

}

Module 1 can import only if I use ComposeExportedValue<IMyApplication>(myApp);

[ModuleExport(typeof(Module1))] 
public class Module1 : IModule
{

    private readonly IRegionManager regionManager;


    [Import]
    private IMyApplication myApp;

}

I would expecting [Export] is enough, but apparently not?

Edit: I removed public MyApplication myApp;to the shell.xaml.cs(more sensible) , from bootstrapper and things get worked. I concluded; MEF composition is in progress and export simply not working. That's why prism internal lib doing exports with ComposeExportedValue(object val)

protected virtual void RegisterBootstrapperProvidedTypes()
{
    this.Container.ComposeExportedValue<ILoggerFacade>(this.Logger);
    this.Container.ComposeExportedValue<IModuleCatalog>(this.ModuleCatalog);
    this.Container.ComposeExportedValue<IServiceLocator>(new MefServiceLocatorAdapter(this.Container));
    this.Container.ComposeExportedValue<AggregateCatalog>(this.AggregateCatalog);
}

Solution

  • I removed public MyApplication myApp;to the shell.xaml.cs(more sensible) , from bootstrapper and things get worked. I concluded; in bootstrapper MEF composition is in progress and export simply not working. That's why prism internal lib doing exports with ComposeExportedValue(object val)

    protected virtual void RegisterBootstrapperProvidedTypes()
    {
        this.Container.ComposeExportedValue<ILoggerFacade>(this.Logger);
        this.Container.ComposeExportedValue<IModuleCatalog>(this.ModuleCatalog);
        this.Container.ComposeExportedValue<IServiceLocator>(new MefServiceLocatorAdapter(this.Container));
        this.Container.ComposeExportedValue<AggregateCatalog>(this.AggregateCatalog);
    }
    

    Also I found one of the purpose for ComposeExportedValue is to make a controlled export; i.e. configure the object, set properties etc. and then export it. Otherwise MEF would export just creating an instance.