У меня есть подкласс DbContext
Декораторы и IDisposable
public class MyContext : DbContext { }
и у меня есть IUnitOfWork
абстракции вокруг MyContext
, который реализует IDisposable
, чтобы гарантировать, что ссылки, такие как MyContext
утилизированы в соответствующее время
public interface IUnitOfWork : IDisposable { }
public class UnitOfWork : IUnitOfWork
{
private readonly MyContext _context;
public UnitOfWork()
{
_context = new MyContext();
}
~UnitOfWork()
{
Dispose(false);
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
private bool _disposed;
protected virtual void Dispose(bool disposing)
{
if (_disposed) return;
if (disposing)
{
if (_context != null) _context.Dispose();
}
_disposed = true;
}
}
Мой UnitOfWork
зарегистрирован на весь срок службы (веб-запроса). У меня есть декораторы IUnitOfWork
, которые могут быть зарегистрированы как переходные или пожизненные, и мой вопрос заключается в том, что они должны делать в отношении реализации IDisposable
- особенно если они или не должны пройти по вызову Dispose()
.
public class UnitOfWorkDecorator : IUnitOfWork
{
private readonly IUnitOfWork _decorated;
public UnitOfWorkDecorator(IUnitOfWork decorated)
{
_decorated = decorated;
}
public void Dispose()
{
//do we pass on the call?
_decorated.Dispose();
}
}
Я вижу 2 варианта (я предполагаю, что вариант 2 правильный ответ):
- Ожидается, что каждый декоратор будет знать, является ли она временной или срок службы области видимости. Если декоратор временно, то он не должен называть
Dispose()
на украшенном экземпляре. Если это срок действия, он должен. - Каждый декоратор должен заботиться только об утилизации себя и должен никогда передать вызов украшенному экземпляру. Контейнер будет управлять вызовом
Dispose()
для каждого объекта в цепочке вызовов в соответствующее время. Объект должен толькоDispose()
экземпляров, которые он инкапсулирует и украшает, не является инкапсуляцией.
Отличный вопрос. Кроме того, вы должны установить переменную _context в * null * в методе Dispose сразу после того, как вы настроили этот контекст. – Maarten
Я согласен с @Maarten: Отличный и очень интересный вопрос. – Steven