在上周的工作中,我们举行了一次会议/演讲,重新思考我们如何做MVC,基于我们老板的大量研究和一些其他SO问题的阅读。对我来说,有一点需要注意的是,当人们说“与数据分离逻辑”时,我可能会更准确地说“与数据源分开逻辑”。如果你做第一个,你可能会成为贫血领域模型的牺牲品。我这是对的吗?
其次,我们了解到MVC不会在任何地方包含您的业务逻辑。这应该位于与Web应用程序不同的单独服务层或BLL中。协调这两点似乎有点棘手 - 一个特定的逻辑是否与数据对象一样,正如基本的OOP原则所规定的那样,还是在一个单独的层中?
这是我现在需要帮助的具体示例。我相信这将属于服务层,但我还有其他问题。假设我有一些行为将多个不同类型的不同实体作为输入。它运行,然后作为输出,它可以修改输入实体,并生成新实体作为记录。在我的情况下,这是一个游戏,但你可以说它就像一个交易。涉及多个人,一些产品和生成的收据。
答案 0 :(得分:4)
让我们先梳理一些术语。您所说的“服务层”通常被称为“域模型”,正如您所说,不要与MVC模型混淆。在最基本的层面上,MVC模型封装了域模型。这两个交互如何不由模式本身定义,但模型存储状态逻辑方式是实现有两种不同的状态:
域状态 - 在现实世界中,这通常会以某种方式存储在数据库中,但域模型不应将任何数据源公开给MVC模型。这允许域模型保持适当的封装。任何改变或访问此数据的逻辑都应该使用相关但抽象的访问器来完成,以便MVC模型访问。
应用程序状态 - 例如“目前正在编辑哪条记录?”
要回答您的问题,这实际上取决于您对数据的处理方式。如果您正在进行任何类型的处理,那么这应该在域模型中完成。如果您只是获取显示所需的数据集合,则MVC模型应查询域模型以检索相关数据。然后,视图应该向模型查询此数据。
所以回答你的问题:
根据经验,几乎任何改变数据或处理来自多个实体的数据的逻辑都应该在域模型中发生。这有两个主要原因:1。可重用性,逻辑可以从任何地方重用。 2.封装。一旦开始将此逻辑放入实体中,您最终会遇到域实体依赖于其他域实体的情况。这导致现实世界中的代码非常脆弱,因为您最终会在以后引入任意规则,例如“这些客户无需输入付款详细信息”。 “这是一个公司客户,他们没有账单地址”,如果你已经建模你的“订单”类构建依赖于一个集合或产品用户和账单地址这将成为一个比处理更大的任务在域模型的早期阶段。