ServiceLocator.Current is null when using VSTO and MEF

Topics: Prism v4 - WPF 4
Sep 23, 2012 at 4:05 PM

Building an addin component for a Prism/WPF project using VSTO/MEF

and running into a ServiceLocator.Current throws a NullReferenceException

 

defined container in VSTO using MEF as follows

            var catalog = new AggregateCatalog();
            catalog.Catalogs.Add(new AssemblyCatalog(this.GetType().Assembly));
            catalog.Catalogs.Add(...);
           
            container = new CompositionContainer(catalog);
            container.SatisfyImportsOnce(this);

all's working well using various libraries/Imports except where the code uses

     ServiceLocator.Current.GetInstance<MyInterface>()

which ofcourse throws a NullReferenceException

Looking into it some more - ServiceLocator is in it's own dll,

 

Question is how is it wired up in Prism/MEF so i can do the same in the addin

thanks

Developer
Sep 25, 2012 at 9:18 PM

Hi,

Based on my understanding in Prism this wiring is achieved in the ConfigureServiceLocator method in both the MefBootstrapper and UnityBootstrapper, where the LocatorProvider is set for for the ServiceLocator, e.g. like this:

protected override void ConfigureServiceLocator()
        {
            IServiceLocator serviceLocator = this.Container.GetExportedValue<IServiceLocator>();
            ServiceLocator.SetLocatorProvider(() => serviceLocator);
        }

Also, as mentioned in the following chapter of the Prism documentation:

In order to replace the container, your container must implement the IServiceLocator interface. The Prism Library provides the UnityServiceLocatorAdapter and the MefServiceLocatorAdapter, and both adapters implement the ISeviceLocator interface by extending the ServiceLocatorImplBase type, in order to leverage IoC and Service Location without tying to a specific implementation.

I hope you find this helpful,

Agustin Adami
http://blogs.southworks.net/aadami

 

Sep 27, 2012 at 3:56 AM

Thanks, I'm using the MEF container

System.ComponentModel.Composition.Hosting.CompositionContainer

vanilla style which does not implement IServiceLocator

For now, I adopted the q&d ( quick & dirty ) approach to meet our deadlines, will revisit it later

 

Thanks again

Sep 22, 2014 at 9:54 AM
Edited Sep 22, 2014 at 9:59 AM
Hi,My code like this
        MainWindowNavViewModel mainWindowNavViewModel1 = ServiceLocator.Current.GetInstance<MainWindowNavViewModel>();

           [Export(typeof(MainWindowNavViewModel))]
           public class MainWindowNavViewModel 
           {}
ServiceLocator.Current.GetInstance work well.

if code like this ,it dose now work.
        MainWindowNavViewModel mainWindowNavViewModel1 = ServiceLocator.Current.GetInstance<MainWindowNavViewModel>();

[Export(typeof(MainWindowNavViewModel))]
public class MainWindowNavViewModel : BaseNavViewModel
{   
}


public abstract class BaseNavViewModel
{
    [Import]
    public BaseMainViewModel MainViewModel { get; set; }
    public ObservableCollection<BaseNavViewModel> NavViewModelCollection { get; set; }
    public BaseNavViewModel()
    {
        NavViewModelCollection = new ObservableCollection<BaseNavViewModel>();
    }
}

BaseNavViewModel、MainWindowNavViewModel in diffrent namespace

Do you kown the reason,thanks