自从我使用实体框架以来,我一直在网上学习有关实体框架的UnitOfWork模式。我对为什么DataContext是公共UnitOfWork构造函数的参数感到困惑。这意味着,如果我在应用程序的另一层中使用UnitOfWork,则另一层必须了解DataContext。这似乎不是很好的关注点分离。我想念什么吗?
UnitOfWork:
public class UnitOfWork : IUnitOfWork
{
private readonly PurchasingDataContext _context;
public UnitOfWork(PurchasingDataContext context)
{
_context = context;
Items = new ItemRepository(_context);
Manufacturers = new LabelerRepository(_context);
Quotes = new QuoteRepository(_context);
Vendors = new VendorRepository(_context);
Contacts = new ContactRepository(_context);
}
public IItemRepository Items { get; private set; }
public ILabelerRepository Manufacturers { get; private set; }
public IQuoteRepository Quotes { get; private set; }
public IVendorRepository Vendors { get; private set; }
public IContactRepository Contacts { get; private set; }
public int Complete()
{
return _context.SaveChanges();
}
public void Dispose()
{
_context.Dispose();
}
}
接口:
public interface IUnitOfWork : IDisposable
{
IContactRepository Contacts { get; }
IItemRepository Items { get; }
ILabelerRepository Manufacturers { get; }
IQuoteRepository Quotes { get; }
IVendorRepository Vendors { get; }
int Complete();
}
答案 0 :(得分:1)
对于为什么在本教程中
DataContext
是public
UnitOfWork
构造函数的参数,我感到困惑。
这是为了将依赖项注入到UoW中。这样,您可以轻松兑现SRP。
借助它,您可以在UoW之外单独管理DataContext
的范围。在不同情况下使用相同的UoW(例如Windows应用程序与Web应用程序)时,这为您提供了很大的灵活性。这样,您可以按照自己的方式扩展数据库事务。
这意味着如果我在应用程序的另一层中使用
UnitOfWork
,则另一层必须知道DataContext
。
是;但并非完全正确。是的,DataContext
的实例应该通过调用层进行托管(创建,注入和处置)。而已。该层无需以任何方式与此实例进行交互。
这似乎不是很好的关注点分离。
为了延续到先前的观点,调用层不需要知道该实例如何工作。所有这些部分都在您的UoW类中进行了抽象。这是明确的关注点分离。
我想念什么吗?
希望您现在知道。
答案 1 :(得分:0)
我首先要问您为什么要在UnitOfWork中创建和公开这些存储库。具有负责一个工作单元和所有存储库所有权的单一类违反了“单一责任原则”。您的IUnitOfWork公开了调用者可能需要或不需要的每个单个存储库,这违反了接口隔离原则。
您应该使用依赖项注入框架来代替此方法,以管理上下文,存储库和工作单元的生命周期。框架应确保为每个请求创建一个实例,并在需要时在依赖关系之间共享。
典型的EntityFramework UnitOfWork类似于:
public interface IUnitOfWork
{
void SaveChanges();
}
具有类似的实现:
public class UnitOfWork : IUnitOfWork
{
private readonly PurchasingDataContext _context;
public UnitOfWork(PurchasingDataContext context)
{
_context = context;
}
public void SaveChanges()
{
return _context.SaveChanges();
}
}