【问题标题】:UnitOfWork as a Container for RepositoriesUnitOfWork 作为存储库的容器
【发布时间】:2013-03-02 21:25:54
【问题描述】:

我有一个看起来像这样的解决方案:

项目 1 共享项目 项目 2

共享项目不是独立的,它通过一个服务层向其他项目公开其功能,该服务层接受一个由其他两个项目注入到构造函数中的 IUnitOfWork:

public SharedService (IUnitOfWork unitOfWork)
{
   ... do stuff ...
}

我遇到的问题是 Project1 和 Project2 有一组重叠但不同的存储库:

Project1: SharedRepository、RepositoryA、RepositoryB ...

Project2: SharedRepository、RepositoryX、RepositoryY ...

我一直看到implementations of Unit Of Work 扮演着存储库容器的角色——你绕过 UoW,然后通过公开它们的公共属性访问存储库:

unitOfWork.SharedRepository.GetSomething();

这种方法的结果是,您最终会得到一个如下所示的工作单元界面:

public interface IUnitOfWork
{
    ISharedRepository SharedRepository();
    IRepositoryA RepositoryA();
    IRepositoryB RepositoryB();
    IRepositoryX RepositoryX();
    IRepositoryY RepositoryY();

    ... etc ...
}

这是我遇到麻烦的地方:接口 IUnitOfWork 现在强制 Project1 和 Project2 实现彼此的存储库。 所以在我看来,使用工作单元作为存储库容器的方法可能是一个有缺陷的概念。

我已经想到了一些可能的替代方案:

1) 将 IUnitOfWork 分成 3 个部分(IProject1UnitOfWork、IProject2UnitOfWork、ISharedUnitOfWork),然后让服务层接受一个 ISharedUnitOfWork 参数。看起来很乱,但它可能会起作用。

2) 将 UnitOfWork 变成类似于服务定位器的东西,它在其中维护存储库的集合,并且您可以注册所需的内容。然后,UoW 的使用者检索它需要的任何存储库。

3) 将工作单元和存储库独立注入到服务层构造函数中:

public SharedService (IUnitOfWork unitOfWork, ISharedRepository repository)
{
   ... do stuff ...
}

你们会如何处理这样的情况?我倾向于选项#3。它需要传递更多的东西,但替代方案似乎不太优雅。

【问题讨论】:

  • ...do stuff... 对工作单元有什么作用?
  • 服务层修改存储库中的数据。工作单元用于协调这些更改并将这些更改提交到数据库。

标签: asp.net-mvc entity-framework architecture unit-of-work repository


【解决方案1】:

所以在我看来,使用工作单元的方法 存储库容器可能是一个有缺陷的概念。

对我也是如此。您示例中的工作单元也是一个伪服务定位器(通常已被视为反模式),因此它违反了 SRP。 UoW 只是一个事务性包装器,围绕着您想要放入其中的任何用例,它不应该知道任何关于存储库或用例中的任何内容的信息。

在那里查看 Dmitry 的答案:How does unit of work class know which repository to call on commit?

所以,对我来说绝对是选项 3。

【讨论】:

    猜你喜欢
    • 2019-03-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-05-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多