Poul K. Sørensen
Poul K. Sørensen

Reputation: 17530

Unity Container and ContainerControlledLifetimeManager when Service Interface is Array

I have the following method:

public void RegisterPlugin<T1>() where T1 : IWebrolePlugin
{
    try
    {
        _container.RegisterType<T1>(new ContainerControlledLifetimeManager());
        _container.RegisterType<IWebrolePlugin, T1>(typeof(T1).Name,new ContainerControlledLifetimeManager());

    }catch(Exception e)
    {
        Trace.TraceError(e.ToString());
    }
}

My problem is that when i do _container.Resolve() i get as expected the same instance of SomePlugin, but when using the following injection constructor it resolves new instances.

I have a the following registration also:

  _container.RegisterType<WebsiteManager>(new InjectionConstructor(typeof(IDirectoryManager), typeof(IStore), typeof(IWebrolePlugin[])));

My problem is that the array of IWebrolePlugin[] is new instances. Can I do anything such my method

public T GetPlugin<T>() where T : IWebrolePlugin
{
    return _container.Resolve<T>();
}

will return the same instances that the WebsiteManager got in its constructor?

Upvotes: 0

Views: 3222

Answers (1)

Randy Levy
Randy Levy

Reputation: 22655

When resolving, Unity first maps the interface to the concrete type by name and uses the concrete type and name as the BuildKey. This BuildKey is used for all aspects of constructing and injecting dependencies (including locating a lifetime manager). That is why the default registration (null name) and a named registration of the same type result in different instances being returned.

The easiest way to use the same instance is to align the registration names between the interface and the concrete type:

public void RegisterPlugin<T1>() where T1 : IWebrolePlugin
{
    try
    {
        _container.RegisterType<T1>(typeof(T1).Name, 
            new ContainerControlledLifetimeManager());
        _container.RegisterType<IWebrolePlugin, T1>(typeof(T1).Name);
    }
    catch (Exception e)
    {
        Trace.TraceError(e.ToString());
    }
}

public T GetPlugin<T>() where T : IWebrolePlugin
{
    return _container.Resolve<T>(typeof(T).Name);
}

This will result in same instance being returned for a straight Resolve and as part of a ResolveAll (for arrays).

Upvotes: 1

Related Questions