Во-первых, вам нужно использовать другой LifetimeManager. TransientLifetimeManager будет разрешать новый экземпляр каждый раз.
container.RegisterType<IFoo, Foo>(
new InjectionConstructor(typeof (IEnumerable<int>),
new ResolvedParameter<IBar1>,
new InjectionParameter<IBar2>(CreateBar2(container)),
new TransientLifetimeManager())
Это означает, что каждый раз, когда IFoo
впрыскивается или разрешено будет вызывать конструктор каждый раз. Однако, похоже, вы вводите метод, который будет выполнен при регистрации - CreateBar2(container)
. Это то же самое, как написание:
var bar2 = CreateBar2(container); // Called once.
container.RegisterType<IFoo, Foo>(
new InjectionConstructor(typeof (IEnumerable<int>),
new ResolvedParameter<IBar1>,
new InjectionParameter<IBar2>(bar2))
Я рекомендую абстрагироваться это в классе, а не нагнетают его. Таким образом, вы также можете контролировать вызовы.
public interface ICreateBar2
{
IBar CreateBar2();
}
public class CreateBar2
{
private IUnityContainer _container;
public CreateBar(IUnityContainer container)
{
_container = container;
}
public IBar CreateBar2()
{
// Do stuff.
return CreateBar2(_container); // Or what you need to do?
}
}
И изменить вашу регистрацию на
container.RegisterType<IFoo, Foo>(
new InjectionConstructor(typeof (IEnumerable<int>),
new ResolvedParameter<IBar1>,
new ResolvedParameter<ICreateBar2>),
new TransientLifetimeManager())
container.RegisterType<ICreateBar2, CreateBar2>(new TransientLifetimeManager());
Или, возможно, RegisterInstance, если она лучше подходит для ваших потребностей?
Не забудьте заменить конструктор IFoo
вместо ICreateBar
. Самое лучшее с этим подходом в том, что вам больше не нужен InjectionConstructor
, так как все параметры могут быть разрешены Unity
.
container.RegisterType<IFoo, Foo>(new TransientLifetimeManager());
Если вы действительно должны держать CreateBar2()
-метода в текущей области, вы можете придать Func
, который фактически возвращает то же значение, как CreateBar2()
.
Я не знаю полностью подпись CreateBar(), но вы можете сделать что-то вроде этого:
container.RegisterType<IFoo, Foo>(
new InjectionConstructor(typeof (IEnumerable<int>),
new ResolvedParameter<IBar1>,
new InjectionParameter<Func<IBar2>>(
new Func<IBar2>(()=> CreateBar2(container)));
Но теперь вам нужно вводить Func<IBar2>
в IFoo
конструктора. Это заставит его выполнять всякий раз, когда вы используете его в конструкторе.
public class Foo : IFoo
{
IBar1 _bar1;
IBar2 _bar2;
public Bar(IBar1 bar1, Func<IBar2> bar2Func)
{
_bar1 = bar1;
_bar2 = bar2Func();
}
}
Использование фабричной инъекции помогло, LifetimeManager не сделал этого и, как я знаю, тип по умолчанию - TransientLifetimeManager. – kvuong
Да. По умолчанию lifetimemanager является временным. – smoksnes