Как я управляю объектным распоряжением, когда я использую МОК?

Мой случай это - Ninject 2.

// normal explicit dispose
using (var dc = new EFContext) 
{
}

Но иногда я должен сохранить контекст дольше или между вызовами функции. Таким образом, я хочу управлять этим поведением через объем МОК.

// if i use this way. how do i make sure object is disposed.
var dc = ninject.Get<IContext>() 

// i cannot use this since the scope can change to singleton. right ??
using (var dc = ninject.Get<IContext>()) 
{
}

Демонстрационные объемы

Container.Bind<IContext>().To<EFContext>().InSingletonScope();
// OR
Container.Bind<IContext>().To<EFContext>().InRequestScope();
5
задан alexandrul 19 May 2010 в 09:20
поделиться

3 ответа

Насколько я знаю (около месяца назад я проводил исследование), Ninject вообще не поддерживает управление жизненным циклом. Castle Windsor и AutoFac (и в некоторой степени StructureMap, но только при использовании вложенных контейнеров) позаботятся об утилизации одноразовых компонентов, которые они создают в надлежащее время.

3
ответ дан 14 December 2019 в 19:08
поделиться

Если у вас есть контроль над интерфейсом ] IContext , добавьте IDisposable в список интерфейсов, от которых он наследуется. Если нет, уменьшите IContext до IDisposable ...

var context = ninject.Get<IContext>();

using ((IDisposable)context)
{
}

У вас также есть возможность изменить интерфейс IContext , чтобы сделать это путем композиции, если вы управляете IContext ...

public interface IContext
{
   // ...

   IDisposable GetUsageHandle();
}

var context = ninject.Get<IContext>();

using (context.GetUsageHandle())
{
}
1
ответ дан 14 December 2019 в 19:08
поделиться

В дополнение к стандартным областям действия Transient, OnePerThread и Singleton, вы можете использовать ActivationBlock для управления временем жизни всего набора объектов. Когда блок удаляется, все объекты, полученные блоком, выходят за пределы области видимости, поэтому синглтоны и другие объекты удаляются, когда их экземпляры запрашиваются блоком активации.

var kernel = new StandardKernel();
kernel.Bind<NotifiesWhenDisposed>().ToSelf();

NotifiesWhenDisposed instance = null;
using(var block = new ActivationBlock(kernel))
{
    instance = block.Get<NotifiesWhenDisposed>();
    instance.IsDisposed.ShouldBeFalse();
}

instance.IsDisposed.ShouldBeTrue();
1
ответ дан 14 December 2019 в 19:08
поделиться