[英]Generic Repository or Specific Repository for each entity?
At the company I work for I have been ordered to update an old MVC app and implement a repository pattern for a SQL database.在我工作的公司,我被要求更新旧的 MVC 应用程序并为 SQL 数据库实现存储库模式。 I have created the context of the database using Entity Framework Database-First and got 23 entities.
我已经使用 Entity Framework Database-First 创建了数据库的上下文并获得了 23 个实体。
Do I need to create a repository for each entity or implement a generic repository for the context?我是否需要为每个实体创建一个存储库或为上下文实现一个通用存储库? I'm asking this because I have found following while searching internet:
我问这个是因为我在搜索互联网时发现了以下内容:
One repository per domain
每个域一个存储库
You should think of a repository as a collection of domain objects in memory.
您应该将存储库视为内存中域对象的集合。 If you're building an application called Vega, you shouldn't have a repository like the following:
如果您正在构建一个名为 Vega 的应用程序,您不应该拥有如下所示的存储库:
public class VegaRepository {}
Instead, you should have a separate repository per domain class, like OrderRepository, ShippingRepository and ProductRepository.
相反,您应该为每个域类拥有一个单独的存储库,例如 OrderRepository、ShippingRepository 和 ProductRepository。
Source: Programming with Mosh: 4 Common Mistakes with the Repository Pattern
资料来源: 使用 Mosh 编程:存储库模式的 4 个常见错误
Does a generic repository work for Entity Framework Database-First?通用存储库是否适用于实体框架数据库优先? This is because I have found following while searching internet:
这是因为我在搜索互联网时发现了以下内容:
Entity framework
实体框架
Do note that the repository pattern is only useful if you have POCOs which are mapped using code first.
请注意,存储库模式仅在您有首先使用代码映射的 POCO 时才有用。 Otherwise you'll just break the abstraction with the entities instead (= the repository pattern isn't very useful then).
否则,您只会用实体打破抽象(= 那时存储库模式不是很有用)。 You can follow this article if you want to get a foundation generated for you.
如果你想为你生成一个基金会,你可以关注这篇文章。
Source: CodeProject: Repository pattern, done right
来源: CodeProject:存储库模式,做得对
To begin with, if you are using full ORM like Entity Framework or NHibernate, you should avoid implementing additional layer of Repository and Unit Of Work.首先,如果您使用完整的 ORM,如实体框架或 NHibernate,您应该避免实现额外的存储库和工作单元层。 This is because;
这是因为; the ORM itself exposes both Generic Repository and Unit Of Work.
ORM 本身公开了通用存储库和工作单元。
In case of EF, your DbContext
is Unit Of Work and DbSet
is Generic Repository.在 EF 的情况下,您的
DbContext
是工作单元,而DbSet
是通用存储库。 In case of NHibernate, it is ISession
itself.在 NHibernate 的情况下,它是
ISession
本身。
Building new wrapper of Generic Repository over same existing one is repeat work.在相同的现有存储库上构建通用存储库的新包装器是重复工作。 Why reinvent the wheel?
为什么要重新发明轮子?
But , some argue that using ORM directly in calling code has following issues:但是,有些人认为在调用代码中直接使用 ORM 存在以下问题:
Apart from all above, one other issue generally discussed is "What if we decide to change ORM in future".除上述之外,另一个普遍讨论的问题是“如果我们决定将来更改 ORM 会怎样”。 This should not be key point while taking decision because:
这不应该是做出决定时的关键点,因为:
Considering four issues mentioned above, it may be necessary to create Repositories even though you are using full ORM - This is per case decision though .考虑到上面提到的四个问题,即使您使用的是完整的 ORM,也可能需要创建存储库 - 尽管这是每个案例的决定。
Even in that case, Generic Repository must be avoided.即使在这种情况下,也必须避免使用通用存储库。 It is considered an anti-pattern.
它被认为是一种反模式。
Why generic repository is anti-pattern?为什么通用存储库是反模式的?
GetById()
, identifier types may be different.GetById()
,标识符类型可能不同。 I suggest you read these ( 1 , 2 , 3 , 4 , 5 ) articles explaining why generic repository is an anti-pattern.我建议您阅读这些( 1 , 2 , 3 , 4 , 5 )文章,这些文章解释了为什么通用存储库是一种反模式。 This other answer discusses about Repository Pattern in general.
这个另一个答案一般讨论了存储库模式。
So, I will suggest:所以,我会建议:
In any case, do not expose Generic Repository to calling code.在任何情况下,不要将通用存储库暴露给调用代码。
Also, do not return IQueryable
from concrete repositories.此外,不要从具体存储库返回
IQueryable
。 This violates basic purpose of existence of Repositories - To abstract data access.这违反了存储库存在的基本目的 - 抽象数据访问。 With exposing
IQueryable
outside the repository, many data access decisions leak into calling code and Repository lose the control over it.由于在存储库外部公开
IQueryable
,许多数据访问决策泄漏到调用代码中,并且存储库失去了对它的控制。
do I need to create a repository for each entity or implement a generic repository for the context
我需要为每个实体创建一个存储库还是为上下文实现一个通用存储库
As suggested above, creating repository for each entity is better approach.如上所述,为每个实体创建存储库是更好的方法。 Note that, Repository should ideally return Domain Model instead of Entity.
请注意,理想情况下,存储库应该返回域模型而不是实体。 But this is different topic for discussion.
但这是不同的讨论话题。
does a generic repository works for EF Database First?
通用存储库是否适用于 EF Database First?
As suggested above, EF itself exposes Generic Repository.如上所述,EF 本身公开了通用存储库。 Building one more layer on it is useless.
在它上面再建一层是没有用的。 Your image is saying the same thing.
你的图片说的是同样的事情。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.