3

我可能在这里分析过度了,但是根据我对 MVC 所做的所有阅读,似乎有很多关于如何做事的意见。

是否有“最佳实践”站点或文档来定义每个 MVC 的职责?

我有几个问题,请记住我使用的是 EF/Repository&UnitOfWork/Service 模式:

1)如何从服务层到视图模型获取领域对象和业务规则的验证结果(错误消息等)?

2) 我正在使用域对象和执行所有业务逻辑的服务层,然后我将域对象发送到控制器并让它们(通过 AutoMapper)将它们转换为视图的视图模型。还有哪些其他类型的事情是控制器的责任?下面的代码可以吗?控制器中的逻辑是否太多?:

public ActionResult SomeAction()
{
    var model = Mapper.Map<DomainObject, ViewModel>(service.QueryReposForData());
    model.SomeCollectionForSelectList = Mapper.Map<IEnumerable<DomainObject>, IEnumerable<ViewModel>>(service.QueryReposForSelectListData());
    return View(model);
}

我不认为控制器中唯一的东西是一条返回视图的行,该视图具有映射到视图模型的对象图?

3) 我认为可以在 ViewModels 上设置属性来指示视图是否可以隐藏某些东西,然后在视图中执行该逻辑?例子:

@if(Model.DisplaySomething)
{
    <div>Something to show</div>
}
else
{
    <div>Something else to show</div>
}

4)我正在考虑让我的服务在写入时将某种TransactionResult对象返回给控制器,以使其成为服务处理事务的责任。所以我会有一个聚合服务,它会启动一个事务(UnitOfWork)做它需要做的事情,然后返回这个TransactionResult可能有错误消息的?我认为我不应该让控制器负责管理事务,而是让它只是将映射到域对象的视图模型传递给服务并让它对其进行操作?

5) 另外,您想使用多少 ActionFilter?我知道这是一个巨大的可扩展点,但我经常发现自己试图将所有模型创建填充到一个过滤器中。

4

3 回答 3

3

优秀的问题!

1)如何从服务层到视图模型获取域对象和业务规则的验证结果(错误消息等)?

我在后端使用 EntityFramework 并在我的模型和实体上实现 IValidatableObject。在模型上,我执行跨字段验证,而在实体上,我执行跨实体验证。

2) 我正在使用域对象和执行所有业务逻辑的服务层,然后我将域对象发送到控制器并让它们(通过 AutoMapper)将它们转换为视图的视图模型。还有哪些其他类型的事情是控制器的责任?下面的代码可以吗?控制器中的逻辑是否太多?:

这段代码很完美。控制器收集数据,将数据转换为模型并将它们提供给视图。

3) 我认为可以在 ViewModels 上设置属性来指示视图是否可以隐藏某些东西,然后在视图中执行该逻辑?例子:

是的,这正是 ViewModel 的用途。捕获视图呈现所需的所有数据和逻辑。

4)我正在考虑让我的服务在写入时将某种 TransactionResult 对象返回给控制器,以使其成为服务处理事务的责任。所以我会有一个聚合服务,它会启动一个事务(UnitOfWork)做它需要做的事情,然后返回这个可能有错误消息的 TransactionResult?我认为我不应该让控制器负责管理事务,而是让它只是将映射到域对象的视图模型传递给服务并让它对其进行操作?

我在我的项目中遇到了一些困难。最后,我把EntityFramework的SaveChanges方法移到了前端。这允许我在前端构建一个事务,然后提交一次。我的 ApiController 中执行更新、创建或删除的每个方法也会执行 SaveChanges。

我使用 ApiControllers 作为后端和实际 Controller 类之间的抽象层。详细地说,我的应用程序都使用普通控制器 (HTML) 和 ApiControllers (REST aka Web API)。两种类型的控制器共享一个用于检索数据的通用接口。

示例: http: //pastebin.com/uL1NGGqH

UnitOfWork 仍然驻留在我的后端的门面后面。我只是将 SaveChanges 暴露给前端。诸如 ValidationExceptions 之类的副作用要么由 ASP.NET MVC 自动处理,要么在自定义 ActionFilters 中捕获。

5) 另外,您想使用多少 ActionFilter?我知道这是一个巨大的可扩展点,但我经常发现自己试图将所有模型创建填充到一个过滤器中。

在我目前正在从事的大型 MVC 项目中,我只使用了少数 ActionFilters。这些 ActionFilters 主要用于强制安全并将异常(例如 ValidationExceptions)转换为 JSON 格式,以便我的客户端验证框架可以处理它。

题外话:你永远不能过度分析。问自己这些 MVC 的基本问题可以让你更好地掌握 MVC 的概念,并使你成为一个更好的开发人员。只要确保你在老板的时间里不要做太多;)

于 2012-08-28T18:33:06.107 回答
3

这里只是基于我们的工作方式的意见。

我们让我们的控制器非常瘦,以至于几乎在所有情况下都会厌食。

对于 ViewModel,我们遵循为每个视图拥有一个 ViewModel 的模式。控制器加载它需要的任何东西,然后启动它。从那里,ViewModel 驱动一切。在我们的世界中,ViewModel 直接绑定到视图,并且不包含将/可能用于应用程序其他部分的代码。它与它需要的较大“模型”(服务层等)的任何部分进行交互,并将内容打包以供视图使用。

对于您的#3 示例,我肯定会说是的——这是我们使用 ViewModel 的方式。

同样,这一切都不是福音——只是我对我们如何处理它的看法。

于 2012-08-28T18:27:55.090 回答
1

同样在这里:

  • 具有通用动作过滤器的基本控制器
  • 验证是使用控制器内的DataAnnotation和模型验证来完成的。
  • 带有注入包装上下文或特定服务层的微型控制器
  • Automapper 映射 ViewModels/EF Pocos。

我并不真正关心实现 UnitOfWork 或显式使用事务,因为 EF4 会自动为SaveChanges中完成的所有更改创建(如果不存在)一个新事务(http://msdn.microsoft.com/en-us/ library/bb896325.aspx我只有一个通用接口,将 Context 的 DbSet 公开为 IQuerable 和 Add/Delete/Find 方法。

但正如所说,这都是个人的。

于 2012-08-28T18:48:48.513 回答