代码之家  ›  专栏  ›  技术社区  ›  Vlad

将控制器逻辑提取到扩展存储库功能的服务中是个好主意吗

  •  2
  • Vlad  · 技术社区  · 16 年前

    我有一个名为list的控制器post-action,它接受一个状态变量,该变量可以是以下值“all”、“active”、“inactive”。然后,我根据控制器内部的“状态”值进行存储库调用。控制器如下所示:

        [HttpPost]
        public ActionResult List(string status)
        {
            return View(GetJobTitlesByStatus(status));
        }
    
        private IList<JobTitle> GetJobTitlesByStatus(string status)
        {
            IList<JobTitle> jobTitles;
    
            switch (status)
            {
                case "All":
                    jobTitles = jobTitleRepository.GetAll();
                    break;
                case "Active":
                    jobTitles = jobTitleRepository.GetActive();
                    break;
                case "Inactive":
                    jobTitles = jobTitleRepository.GetInactive();
                    break;
                default:
                    jobTitles = new List<JobTitle>();
                    break;
            }
        }
    

    我决定switch语句中的代码太多,不能在控制器内部,所以我将其提取到一个服务中,然后该服务进行适当的存储库调用。例如:

    public class JobTitleService : JobTitleRepository, IJobTitleService, IJobTitleRepository
    {
        public JobTitleService(ISession session) : base(session) { }
        public IList<JobTitle> GetJobTitlesByStatus(string status)
        {
            IList<JobTitle> jobTitles;
    
            switch (status)
            {
                case "All":
                    jobTitles = base.GetAll();
                    break;
                case "Active":
                    jobTitles = base.GetActive();
                    break;
                case "Inactive":
                    jobTitles = base.GetInactive();
                    break;
                default:
                    jobTitles = new List<JobTitle>();
                    break;
            }
    
            return jobTitles;
        }
    }
    

    我个人认为这很好,特别是因为我使用依赖注入将服务引入控制器。我有以下问题:

    1)您认为从控制器中提取switch语句逻辑是一个好主意吗?
    2)您认为JobTitleRepository继承JobTitleService优于 是否将IjobTitleRepository传递给服务的构造函数(使用依赖项注入)?
    3)JobTitleService使用的设计模式是否有特殊名称?

    2 回复  |  直到 16 年前
        1
  •  3
  •   FinnNk    16 年前
    1. 是-控制器应负责选择结果,准备模型,然后将模型传递给视图进行渲染。其他的一切都应该委托给其他地方,通常是服务。直接取自 wikipedia :

      控制器接收输入和 通过打电话启动响应 在模型对象上。控制器接受 从用户输入并指示 要执行操作的模型和视区 基于该输入。

    2. 不,您的服务不应该从存储库继承。该服务需要与存储库协作来完成其功能,因此它是一种“有-无”的IS-A关系。现在,这可能并不明显,因为您的服务只是对存储库的传递,但一旦您的服务开始执行应该执行的服务(协调一个或多个合作者的操作),它将立即变得明显,因为您只能从其中一个合作者继承。

      事实上,在这种情况下,如果您的服务只是一个围绕存储库的直接包装器,那么它不会添加任何内容,只是一个间接层——如果它保持如此简单,那么我将忽略它并直接查询存储库。但通常情况下,事情不会那么简单。

    3. 不,不是真的。

        2
  •  2
  •   David    16 年前

    1)是的,业务逻辑不应该在控制器中。控制器实际上只是将表示连接到逻辑。理想情况下,逻辑是在一个更面向对象的方法中执行的,而不是在一个更为程序化的方法中执行的,但是不要因此而被劝阻。只要代码简单且可支持,过程就不是坏事。这个设计为您做的是允许您在需要时将服务类转移到实际的单独服务中。

    2)我很难量化它,但是我会犹豫是否要从存储库继承服务。在这个特定的设计中,我将把服务看作是存储业务逻辑过程的地方,而存储库将作为支持持久性的组件注入(理想情况下,业务逻辑不应该支持持久性)。我只是认为它能更清晰地区分关注点,并且在系统增长时更容易完全摸索设计。但这可能只是我个人的观点。

    3)我确信有一个正式的名字可以放在简历的某个地方:)“面向服务的体系结构”和其他的流行语浮现在我的脑海中。我对术语从来就不是很在行,所以在这方面我帮不了什么忙。但是有很多关于这个主题的阅读材料。这看起来是一个很好的读物: http://msdn.microsoft.com/en-us/library/ms954638.aspx 也可以在这里寻找资源: http://www.soapatterns.org/

    推荐文章