如何配置工作单元

时间:2011-12-01 17:48:51

标签: asp.net-mvc asp.net-mvc-3 dependency-injection unit-of-work

我正在取得进展,但仍然在多层MVC应用程序中努力工作单元。查看此处的示例:http://www.asp.net/entity-framework/tutorials/implementing-the-repository-and-unit-of-work-patterns-in-an-asp-net-mvc-application UoW包装所有存储库,并为每个存储库提供相同dbcontext的副本。然后控制器可以使用存储库,例如:

var courses = unitOfWork.CourseRepository.Get(includeProperties: "Department");

现在假设您有一个访问存储库的服务层。您可以对其进行配置,使其依赖于IUnitOfWork实现,然后通过Unity传入EfUnitOfWork实现。然后,当服务完成某个任务时,它可以调用unitOfWork.context.SaveChanges()。但是这种方法隐藏了服务的真正依赖性;它需要的存储库。这也意味着测试服务需要您构建一个完整的UoW。

所以我认为必须有一种不同的方法,并且我想知道以下其中一种或我上面提到的(或其他什么!)是正确的方法:

  • 服务接受相同的存储库参数以及IUnitOfWork。这些存储库与Unity提供的dbContext副本相连。 EfUnitOfWork也使用相同的副本连接。然后,服务可以像以前一样使用存储库,一旦完成使用EfUnitOfWork提交。
  • Service只接受IUnitOfWork,但通过向其传递IUnitOfWork.dbcontext中传递的副本来设置其所需的存储库

请帮忙!

詹姆斯

2 个答案:

答案 0 :(得分:0)

服务层通常设计为使每个方法执行完整操作。服务层方法负责处理工作单元。使用这种方法,工作单元不应跨越对服务层的多次调用。

如果您想要一起执行更大的更新块,则可以使用事务。创建一个新的TransactionScope,然后在其中调用几个服务层方法:

using(TransactionScope ts = new TransactionScope())
{
  ServiceLayer.DoSomething();
  ServiceLayer.DoSomethingElse();
  ts.Commit();
}

答案 1 :(得分:0)

对,所以我已经进一步探讨了这个问题,我得出了以下结论,所以我想在这里记录下来帮助别人,或者如果我的发现是错误的,我可以纠正。

DbContext 工作单位。我只需要将这个工作单元传递给已实现的EFRepository类。它不需要进入Service类。那么Service类如何调用context.SaveChanges()以确保在没有DbContext实例时协调所有相关更改?它调用EFRepository.Save(),如下所示:

public void Save()
    {
        context.SaveChanges();
    }

使用此方法,服务类仅依赖于存储库。这将是清楚的,可以嘲笑进行测试。当Unity将所需的Repository对象注入服务时,它可以为每个Repository提供相同的DbContext。此外,只有存储库可以访问DbContext。

所有这些都可能是显而易见的,但它让我难过。或者它可能是完全错误的,在这种情况下请告诉我!

詹姆斯