我正在开始一个新项目,并决定尝试合并DDD模式,还包括Linq to Entities。当我查看EF的ObjectContext时,它似乎正在执行Repository和Unit of Work模式的功能:
存储库的意思是底层数据级接口是从实体表示中抽象出来的,我可以通过ObjectContext请求和保存数据。
工作单元,我可以将所有插入/更新写入objectContext并在执行SaveChanges()时一次性执行它们。
将这些模式的另一层放在EF ObjectContext之上似乎是多余的?似乎Model类可以使用'partial class'直接合并到EF生成的实体之上。
我是DDD的新手,所以如果我在这里遗漏了什么,请告诉我。
答案 0 :(得分:17)
我认为实体框架不是Repository的良好实现,因为:
另一方面,一旦有了ObjectContext,实现Repository模式就变得微不足道了。实际上,对于不是特别复杂的情况,Repository是ObjectContext和Entity类型的包装器。
答案 1 :(得分:7)
我想说你应该把ObjectContext看作你的UnitOfWork,而不是作为一个存储库。
ObjectContext不能是存储库-imho-因为它是'泛型'。 您应该创建自己的存储库,它们在常规CRUD方法旁边有专门的方法(例如GetCustomersWithGoldStatus)。
所以,我要做的是创建存储库(每个聚合根一个),让这些存储库使用ObjectContext。
答案 2 :(得分:0)
我喜欢拥有存储库层,原因如下:
EF gotcha's
当你看一些关于EF(Code First版本)的当前教程时,显然有许多问题需要处理,特别是在对象图(包含实体的实体)和断开连接的场景之间。我认为存储库层非常适合将它们包装在一个地方。
数据访问机制的清晰画面
存储库提供有关BL如何访问和更新数据存储的特定图片。它公开了具有明确单一目的的方法,并且可以独立于BL进行测试。来自教科书的标准示例,查找()来查找单个实体。一个更具特定于应用程序的示例,清除()以清除数据库表。
优化的地方
使用香草EF时,你不可避免地会遇到性能问题。我使用存储库来隐藏BL的优化机制。
示例,
GetKeys()从表中投影缓存的密钥(用于插入/更新决策)。只读密钥比读取完整实体更快,占用的内存更少。
通过SqlBulkCopy批量加载。 EF将通过单个SQL语句插入。如果您希望单个语句插入多行,SqlBulkCopy是一个很好的机制。存储库封装了它并为SqlBulkCopy提供了元数据。除了Insert方法之外,还需要一个StartBatch()和EndBatch()方法,它也是UnitOfWork层的参数。