0

我正在 ASP.NET MVC 4 中构建一个相对简单的 webapp,使用实体框架与 MS SQL Server 对话。未来有很多扩展应用程序的空间,所以我的目标是在代码中最大化可重用性和适应性的模式,以节省以后的工作。这个想法是:

  • 工作单元模式,通过仅在每组操作结束时提交更改来保存数据库问题。
  • 使用通用存储库,BaseRepository<T>因为存储库基本相同;奇怪的异常可以扩展和添加它的附加方法。
  • 依赖注入将这些存储库绑定到IRepository<T>控制器将使用的存储库,这样我就可以毫不费力地切换数据存储方法等(不仅仅是为了最佳实践;这种情况很有可能发生)。我正在为此使用 Ninject。

我以前没有真正从头开始尝试过这样的事情,所以我一直在阅读,我想我在某个地方搞糊涂了。到目前为止,我有一个IRepository<T>由 实现的接口BaseRepository<T>,它包含一个DataContext传递给其构造函数的实例。该接口具有 Add、Update、Delete 和各种类型的 Get 方法(按 ID 单、按谓词单、按谓词分组、全部)。唯一不适合此接口的存储库(到目前为止)是用户存储库,它添加User Login(string username, string password)以允许登录(其实现处理所有的加盐、散列、检查等)。

根据我的阅读,我现在需要一个UnitOfWork包含所有存储库实例的类。此工作单元将公开存储库以及 SaveChanges() 方法。当我想操作数据时,我会实例化一个工作单元,访问其上的存储库(根据需要进行实例化),然后保存。如果有任何失败,数据库中不会发生任何变化,因为它最终不会到达单个保存。这一切都很好。我的问题是,我能找到的所有示例似乎都在做以下两件事之一:

  • 有些将数据上下文传递到工作单元,从中检索各种存储库。DbContext这通过在我的工作单元中具有我的实体框架特定(或从它继承的类)来否定 DI 的观点。
  • 有些人调用 Get 方法来请求存储库,这是服务定位器模式,如果不是反模式,它至少是不受欢迎的,无论哪种方式,我都想在这里避免它。

我是否需要为我的数据源创建一个接口并将其也注入到工作单元中?我找不到任何足够清晰和/或完整的文档来解释。

编辑

我想我已经把它复杂化了。我现在将我的存储库和工作单元合二为一——我的存储库是完全通用的,所以这只给了我一些通用方法(添加、删除、更新和几种 Get)以及 SaveChanges 方法。这给了我一个工人类接口;然后我可以有一个工厂类来提供它的实例(也是接口的)。如果我也有这个 worker 实现IDisposable,那么我可以在作用域块中使用它。所以现在我的控制器可以做这样的事情:

using (var worker = DataAccess.BeginTransaction())
{
    Product item = worker.Get<Product>(p => p.ID == prodName);
    //stuff...
    worker.SaveChanges();
}

如果在 之前出现问题SaveChanges(),那么当它退出范围块并释放工作人员时,所有更改都将被丢弃。我可以使用依赖注入为该字段提供具体实现,该DataAccess字段被传递到基本控制器构造函数中。业务逻辑都在控制器中并与IQueryable对象一起使用,因此我可以将DataAccess提供者对象切换为我喜欢的任何东西,只要它实现了IRepository接口;任何地方都没有特定于实体框架的东西。

那么,对这个实现有什么想法吗?这是在正确的轨道上吗?

4

1 回答 1

1

我更喜欢拥有UnitOfWorkUnitOfWorkFactory注入存储库,这样每次添加新存储库时我都不需要打扰它。UnitOfWork 的职责是管理事务。

是我的意思的一个例子。

于 2013-03-16T13:25:40.080 回答