ReactiveUI 5 has just been released (although I’ve been playing with the -pre-release alpha for a while), and one of the shiny new things it brings is a simplified Service Location model. This is fine in the most part, for most applications. But, when you have some complicated dependencies between objects (ignoring the fact you might be heading towards a constructor over-injection anti-pattern), you may feel you need to use a full IoC container, like Structuremap, to do the heavy work.

All we need to do first is implement {csharp}IMutableDependencyResolver{/csharp}, and replace the default implementation in ReactiveUi with our new one.


    public class StructureMapDependencyResolver : IMutableDependencyResolver
    {
        public StructureMapDependencyResolver()
        {
            ObjectFactory.Initialize(init => init.Scan(scan =>
                          {
                              scan.TheCallingAssembly();
                              scan.LookForRegistries();
                              scan.WithDefaultConventions();
                          }));

        }

        public void Dispose()
        {
        }

        public object GetService(Type serviceType, string contract = null)
        {
            return string.IsNullOrEmpty(contract)
                       ? ObjectFactory.GetInstance(serviceType)
                       : ObjectFactory.GetNamedInstance(serviceType, contract);
        }

        public IEnumerable<object> GetServices(Type serviceType, string contract = null)
        {
            return ObjectFactory.GetAllInstances(serviceType).Cast<object>();
        }

        public void Register(Func<object> factory, Type serviceType, string contract = null)
        {
            ObjectFactory.Configure(x => x.For(serviceType).Use(factory()));
        }
    }

Then, make ReactiveUI use it.


var resolver = new StructureMapDependencyResolver();
RxApp.InitializeCustomResolver((o, type) => resolver.Register(() => o, type));
RxApp.DependencyResolver = resolver;

The second line there is very important: ReactiveUi uses the DependecyResolver internally, so if you use your own, you need to initialise it with the default ReactiveUi types, or else The Bad Things™ will happen.