C# 构建Asp.net MVC控制器文件夹以实现更好的内聚性

C# 构建Asp.net MVC控制器文件夹以实现更好的内聚性,c#,asp.net,asp.net-mvc,C#,Asp.net,Asp.net Mvc,在构建复杂的应用程序时,控制器可能会变得笨拙且非常大,这可能意味着您将它们拆分为单独的控制器。这可能不合适,因为它将反映在用户体验中。他们将在URI中看到控制器名称 例如:MVC附带的默认项目有一个AccountController,它具有登录、注销、注册等操作。。这似乎违反了法律 因此,问题是如何解决这个问题并将关注点分离出来?最初的响应可能只是创建单独的控制器。即 AccountLoginController AccountRegisterController 但从客户的角度来看,这并不

在构建复杂的应用程序时,控制器可能会变得笨拙且非常大,这可能意味着您将它们拆分为单独的控制器。这可能不合适,因为它将反映在用户体验中。他们将在URI中看到控制器名称

例如:MVC附带的默认项目有一个AccountController,它具有登录、注销、注册等操作。。这似乎违反了法律

因此,问题是如何解决这个问题并将关注点分离出来?最初的响应可能只是创建单独的控制器。即

AccountLoginController

AccountRegisterController
但从客户的角度来看,这并不是一个很好的体验,因为它会在请求资源时影响URI

一个解决方案是为每个控制器提供单独的文件夹,其中包含用于操作的单独类文件,每个类文件都有一个单独的职责,就像这样

Controllers (folder)
    Account  (folder)
        Register.cs
        Login.cs
        Logout.cs
    AnotherController (folder)
        Actionfile.cs
        Actionfile.cs
上述内容将分离出功能,并进行了详细说明

这是一个很长的解释,但我的问题是

  • 以前有人实施过吗

  • 如果是的话,你怎么做

  • 你对这种模式有什么想法


    • 这取决于你所说的单一责任

      如果您的意思是将身份验证作为一种责任,那么开箱即用控制器就是这样的完美。登录、注销和注册都是同一件事的一部分——身份验证。因此,它们的代码在同一个控制器中是有意义的

      如果将单一责任原则发挥到荒谬的极端,那么在一个文件中永远不会有超过一个类和一个函数

      您必须在可读性/可维护性与关注点分离之间找到平衡。在这种情况下,这太过分了

      另外,请记住,MVC完全是关于,这意味着如果您按照约定命名控制器和视图,那么它们将是可发现的,并且您将有更少的配置和路由问题

      话虽如此,如果您决定采用非传统的控制器命名约定,也就是说,您可以实现自己的控制器发现代码,这将允许您使用不同的约定。从上面链接的文章中:

      public class ControllerConvention : TypeRules, ITypeScanner {
        public void Process(Type type, PluginGraph graph) {
           if (CanBeCast(typeof (IController), type)) {
           string name = type.Name.Replace("Controller", "").ToLower();
            graph.AddType(typeof(IController), type, name);
          }
        }
      }
      
      你看了吗

      “区域允许您将大型项目组织为多个较小的部分,以便管理大型Web应用程序的复杂性。每个部分(“区域”)通常表示大型网站的一个单独部分,用于将相关的控制器和视图集分组。”


      简而言之,区域是项目中的一个文件夹,它有自己的用于控制器、模型和视图的子文件夹。

      配置之上的约定非常适合快速启动,或者用于URI从长期意义上来说无关紧要的后端应用程序。但对于我在MVC上做过的任何面向公众的网站,基于惯例的路线都没有发布,原因如下:

      • 你的URL就是你的API。你应该控制它们,并知道你在哪里发布什么
      • 我有点偏执,我不喜欢可能有东西通过url欺骗泄露到我的应用程序中

      自定义路由还允许您根据操作将/Foo转到fooocontroller和FooBarController。你甚至可以利用这些区域,而不将它们公开。

      你说得很好,但我认为这里的困惑在于控制器到底是什么。在MVC模式中,可以将控制器视为一组操作方法的命名空间

      让我们以.NET的“系统”命名空间为例。“System.Data”和“System.Core”有两个非常不同的职责,但它们被分组在“System”包装下

      当访问控制器的操作时,通常会使用类似{controller}/{action}的路由

      “AccountController”的“Account”部分映射到{controller},“AccountController”中的方法映射到{action}

      我建议您构建一个类库来处理您的业务逻辑,并将您的操作路由到此库。您可以完全按照上面所述构建类,将操作的路由值传递给库,并返回视图的模型

      Register.cs可以是一个静态类,您可以从AccountController中的action方法调用它

      例如:

      “/帐户/注册”->

      控制器:

      public class AccountController : Controller
      {
           public ActionResult Register()
           {
               return View("Register", Register.RegisterUser());
           }
      }
      
      控制器逻辑:

      public static class Register
      {
           public static RegisterModel RegisterUser()
           {
               // Handle application logic here and build your model
               return new RegisterModel() { PasswordLength = 12 };
           }
      }
      
      型号:

      public class RegisterModel
      {
          public int PasswordLength { get; set; }
      }
      

      我理解你的观点,但我发现在更大的MVC项目中,情况正好相反。它们越大,我就越欣赏这些惯例,因为它们有助于防止无法维护的问题。+1-你的凝聚力和单一责任感是相当主观的。当当前ASP.NETMVC的组织方式与其他MVC实现非常相似时,提问者是如何追逐梦想模式的。当你偏离正轨时,你要么是天才,要么完全疯了。你的电话为什么强调URI?大多数(99%+)用户不会关心“.com”之后的任何内容。为什么它是
      /Account/Register
      还是
      /AccountRegister
      ?在每个MVC教程都将路由作为第一步之前,.net开发人员根本不关心URI,这让我觉得很可笑。你去过易趣或亚马逊吗?那些URI很可怕,但它们仍然是成功的站点。你知道为什么吗?因为他们关心用户体验。与用户在地址栏中看到的内容相比,我更担心实际站点上的用户体验(功能、布局、菜单导航等)/rant@Ryan我不知道你的评论有什么意义?声明.net开发人员“…直到…”才关心URI的问题”只是一种推测性的观点,并不真实。傅