21

我发现 MVC 无法识别控制器,除非它在类名后面附加了“控制器”,这很荒谬。这个答案提到ControllerDescriptorandControllerTypeCache作为 MVC 中设置此约定的两个地方。

我的问题是为什么?这显然不是配置的约定,如IsControllerType检查ControllerTypeCache类:

  • 是否公开
  • 不抽象
  • 实现IController
  • 以。。结束"Controller"

有人知道这是什么原因吗?毕竟所有控制器都可能在一个实际的 MVC 项目中,在一个名为“Controllers”的文件夹中,然后简单地双击该文件将向我们显示该类继承了Controller.

对我来说似乎很愚蠢-但我想知道他们这样做是否有实际原因。

编辑

刚刚看到Phil Haack 昨天发表的这篇博客文章,他讨论了这个大会的决定——他和我的想法一样——可能有点毫无意义!

4

3 回答 3

16

定制控制器工厂

您始终可以提供一个自定义控制器工厂,以不同方式解析这些类。而且我同意控制器不需要附加控制器类型名称,因为毕竟它们就像任何其他类一样。无论如何,它们的 OOP 祖先类型将它们定义为控制器 ( IController, Controller...)

可能是 Visual Studio?

尽管它可能与 Visual Studio 有关。类似于属性类。也许 Visual Studio 不会为不以Controller结尾的类提供额外的上下文菜单项。当处于控制器操作中时,您可以轻松导航(或创建)到匹配的视图。

约定很好

所以说专家和我同意。.net 框架中还有其他类似的约定,但人们不会抱怨它们。

想想collectionsdictionariesattributeslists和其他类型也使用类似的后缀而没有特别的原因。无论哪种方式它们都可以工作,但它们的用户(开发人员)更容易识别它们,他们本能地知道它们应该如何工作以及何时使用它们。

根据 Asp.net MVC 团队的类型冲突

想象一下,有一个ProductController可能处理Product应用程序模型实体实例。由于没有控制器命名约定,我们将有两种具有相同名称的类型,因此必须始终提供命名空间来区分两者。但是因为我们确实有这个约定,所以这不是必需的,也不会发生类型冲突。

public class ProductController : Controller
{
    public ActionResult Index()
    {
        // we'd have to distinguish this Product type here
        IEnumerable<Product> result = GetProducts();
        return View(result);
    }
    ...
}
于 2012-07-19T09:27:19.220 回答
0

需要前 2 个以便 mvc 可以实例化控制器,需要第 3 个以便 mvc 知道如何使用控制器(调用Execute方法),第 4 个我想只是为了更快地找到类型。

于 2012-07-19T09:16:59.707 回答
0

是的,约定很好,但我认为这不是约定问题。这是从解决方案域中为正在使用的模式选择一个好的名称的问题。

例如,如果处理产品的 UX 涉及到一个列表,那么您可以简单地调用控制器 ProductList,它不必与 List 混淆。作为人类,我们每天都可以根据上下文轻松消除歧义,软件中的命名也不例外。现在控制器的作用是协调。以我们的 ProductList 为例。它将协调诸如 ProductList.sort(byField)、ProductList.delete(product) 之类的操作。

就利用约定优于配置的概念而言,可以在元级别上做到这一点。在 .Net 中,可以使用属性来识别控制器或模型。

有什么大不了的?在名称中说明模式会导致懒惰的命名,从而导致懒惰的建模。名称不仅仅是一个名称,它还选择了一个概念,您将使用该概念来对解决方案域进行建模,其含义决定了哪些代码代表该概念以及该代码耦合到哪些其他代码。您的名称越通用和/或模棱两可,您就越会邀请您的设计以更难维护的方式进行扩展和更改。

于 2014-09-26T05:41:49.247 回答