论坛首页 Java企业应用论坛

看看Rod Johnson怎么讲Domain Object

浏览 13097 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2005-03-24  
我手里面没有Martin Fowler的POEAA,但是刚好手里面有Rod Johnson的《without EJB》,Rod Johnson在第10章《持久化》里面比较清楚的论述了这个问题:

引用
A simple form of O/R mapping is an active record (POEAA). In this approach, every row of a mapped table is represented by one instance of the corresponding gateway class. Such a persistent class features insert, update, and delete methods as explicit persistence operations to be invoked by business controller logic. Additionally, there will typically be a finder class per mapped table, with finder methods to retrieve persistent objects in the first place. Business logic is either kept outside the persistent objects in workflow methods or defined on the objects themselves.


我们一直提到的只有getter/setter的纯数据类,Martin Fowler有一个专用词汇,叫做“Active Record”。传统的Entity Bean和现在的一些SQL Mapping Tools如iBATIS下面的domain object就是这种模型,这也是Marin Fowler指的贫血的domain object。

引用
In contrast to “active records” that define their own persistence operations within the domain class, a data mapper (POEAA), also commonly known as O/R mapper, aims to “move data between objects and a database while keeping them independent of each other and the mapper itself.” This separates business and persistence aspects into distinct classes: The domain class will focus on data representation and domain logic, while the data mapper will be concerned with the persistence aspects. The term transparent persistence is often used to refer to such non-intrusive persistence mechanisms that also provide unit-of-work semantics (discussed shortly). It has the important virtue that the difficult problem of data mapping can be addressed largely by a generic framework, rather than application code. Popular products implementing this pattern are Hibernate, TopLink, and various O/R-based JDO implementations.


请注意,这段话中很重要的一个词汇“transparent persistence”,由于现在O/R Mapping(Hibernate,JDO,TopLink,etc)的出现,使得很多domain object的逻辑可以直接放在domain object中完成,而持久化会透明的进行,一个最简单的例子就是 forum.getTopics().remove(topic),这在domain object来说是一个简单的Java集合操作,但是O/R Mapping实际上会执行数据库持久化的动作,删除一个topic数据库记录,这就是所谓的“transparent persistence”(透明的持久化)的含义。在这种情况下,domain object应该丰富起来了。

再看下面最重要的一节:

Transparent Persistence and Behavior in Domain Objects

引用
Workflow methods at the business facade level are still responsible for transaction demarcation, for retrieving persistent objects in the first place, and for operations that span multiple objects, but no longer for domain logic that really belongs to the domain model.


这段话明白无误的讲清楚了domain object应该包含什么逻辑,不应该包含什么逻辑。domain object包含的逻辑,这里称之为“domain logic”,这些domain logic应该最小化的依赖于DAO,而我们讨论的那些需要持久化操作参与的事务性逻辑,这里称之为“workflow methods”,这些“workflow methods”应该放在“business facade”,而不应该放在domain object里面。

引用
What logic to put into domain classes versus what to put into workflow controllers should be decided case by case. Operations that are reusable across multiple use cases should normally be part of domain classes. Single use cases that are hardly reusable are candidates for controller methods; so are operations that span multiple domain objects.


最后Rod Johnson给出来一个区分的“business workflow logic”和“domain logic”的准则:视具体情况而定,紧密结合domain object的,可重用度很高的操作可能是domain logic,应该放在domain object里面;比较难重用的控制逻辑方法,特别是可跨越多个domain object的操作则放在business facade object里面。

没有直接看到POEAA,不过由Rod Johnson的话判断起来,Martin Fowler的domain object之外,一定有business object,而那些涉及多个domain object协作,或者不涉及domain object协作,但是不紧密结合domain object本身的操作是属于business object的,而不是属于domain object的。也就是说上个帖子中讨论的案例中,并不是所有的逻辑都塞到Forum里面去,而是Forum之外一定有一个ForumManager类。同样的,上面帖子jackyz提到的 loadForumByPrimaryKey方法也不应该放在Forum中,而是应该放在Forum之外,由Busniess Object来实现,即:

forumManager.loadForumByPrimaryKey(forumId);;


所以说,partech的说法是正确的,我的观点也是正确的,而Archie的观点是不对的。
   发表时间:2005-03-24  
robbin 写道
我手里面没有Martin Fowler的POEAA,但是刚好手里面有Rod Johnson的《without EJB》,Rod Johnson在第10章《持久化》里面比较清楚的论述了这个问题:

引用
A simple form of O/R mapping is an active record (POEAA). In this approach, every row of a mapped table is represented by one instance of the corresponding gateway class. Such a persistent class features insert, update, and delete methods as explicit persistence operations to be invoked by business controller logic. Additionally, there will typically be a finder class per mapped table, with finder methods to retrieve persistent objects in the first place. Business logic is either kept outside the persistent objects in workflow methods or defined on the objects themselves.


我们一直提到的只有getter/setter的纯数据类,Martin Fowler有一个专用词汇,叫做“Active Record”。传统的Entity Bean和现在的一些SQL Mapping Tools如iBATIS下面的domain object就是这种模型,这也是Marin Fowler指的贫血的domain object。

引用
In contrast to “active records” that define their own persistence operations within the domain class, a data mapper (POEAA), also commonly known as O/R mapper, aims to “move data between objects and a database while keeping them independent of each other and the mapper itself.” This separates business and persistence aspects into distinct classes: The domain class will focus on data representation and domain logic, while the data mapper will be concerned with the persistence aspects. The term transparent persistence is often used to refer to such non-intrusive persistence mechanisms that also provide unit-of-work semantics (discussed shortly). It has the important virtue that the difficult problem of data mapping can be addressed largely by a generic framework, rather than application code. Popular products implementing this pattern are Hibernate, TopLink, and various O/R-based JDO implementations.


请注意,这段话中很重要的一个词汇“transparent persistence”,由于现在O/R Mapping(Hibernate,JDO,TopLink,etc)的出现,使得很多domain object的逻辑可以直接放在domain object中完成,而持久化会透明的进行,一个最简单的例子就是 forum.getTopics().remove(topic),这在domain object来说是一个简单的Java集合操作,但是O/R Mapping实际上会执行数据库持久化的动作,删除一个topic数据库记录,这就是所谓的“transparent persistence”(透明的持久化)的含义。在这种情况下,domain object应该丰富起来了。

再看下面最重要的一节:

Transparent Persistence and Behavior in Domain Objects

引用
Workflow methods at the business facade level are still responsible for transaction demarcation, for retrieving persistent objects in the first place, and for operations that span multiple objects, but no longer for domain logic that really belongs to the domain model.


这段话明白无误的讲清楚了domain object应该包含什么逻辑,不应该包含什么逻辑。domain object包含的逻辑,这里称之为“domain logic”,这些domain logic应该最小化的依赖于DAO,而我们讨论的那些需要持久化操作参与的事务性逻辑,这里称之为“workflow methods”,这些“workflow methods”应该放在“business facade”,而不应该放在domain object里面。

引用
What logic to put into domain classes versus what to put into workflow controllers should be decided case by case. Operations that are reusable across multiple use cases should normally be part of domain classes. Single use cases that are hardly reusable are candidates for controller methods; so are operations that span multiple domain objects.


最后Rod Johnson给出来一个区分的“business workflow logic”和“domain logic”的准则:视具体情况而定,紧密结合domain object的,可重用度很高的操作可能是domain logic,应该放在domain object里面;比较难重用的控制逻辑方法,特别是可跨越多个domain object的操作则放在business facade object里面。

没有直接看到POEAA,不过由Rod Johnson的话判断起来,Martin Fowler的domain object之外,一定有business object,而那些涉及多个domain object协作,或者不涉及domain object协作,但是不紧密结合domain object本身的操作是属于business object的,而不是属于domain object的。也就是说上个帖子中讨论的案例中,并不是所有的逻辑都塞到Forum里面去,而是Forum之外一定有一个ForumManager类。同样的,上面帖子jackyz提到的 loadForumByPrimaryKey方法也不应该放在Forum中,而是应该放在Forum之外,由Busniess Object来实现,即:

forumManager.loadForumByPrimaryKey(forumId);;


所以说,partech的说法是正确的,我的观点也是正确的,而Archie的观点是不对的。


我没说什么逻辑都放在Domain Objects里边啊
0 请登录后投票
   发表时间:2005-03-24  
你的主张是只有一个Forum,而没有ForumManager(或者ForumService)吧?

我的意思就是说domain object拥有的只是domain logic,而不拥有本来是business object的workflow business logic。所以如果模型中没有ForumManager(或者承担相同责任的business facade),那就是不对的。

当然指责谁对谁不对并不是我的目的,我的目的只是要说明一下,即使是Martin Folwer的domain model中,他也要区分domain object和business object这两类对象。而前面我们曾经讨论过一种方案,就是把domain object和business object合二为一,现在来看,显然这种方案不是Martin Fowler的本意。我唯一的目的就是澄清这一点就足够了。
0 请登录后投票
   发表时间:2005-03-24  
robbin 写道
你的主张是只有一个Forum,而没有ForumManager(或者ForumService)吧?

我的意思就是说domain object拥有的只是domain logic,而不拥有本来是business object的workflow business logic。所以如果模型中没有ForumManager(或者承担相同责任的business facade),那就是不对的。

当然指责谁对谁不对并不是我的目的,我的目的只是要说明一下,即使是Martin Folwer的domain model中,他也要区分domain object和business object这两类对象。而前面我们曾经讨论过一种方案,就是把domain object和business object合二为一,现在来看,显然这种方案不是Martin Fowler的本意。我唯一的目的就是澄清这一点就足够了。


我的主张和partech是一样的。
只是想能不能做到DAO的实现不去依赖DomainObjects。不过看来是不可能的。起始向上依赖也没什么不好的,正好解开了一直向下依赖的耦合。
Service Layer ----->DomainObject<--------DAOImpl------>DB
0 请登录后投票
   发表时间:2005-03-24  
引用

这段话明白无误的讲清楚了domain object应该包含什么逻辑,不应该包含什么逻辑。domain object包含的逻辑,这里称之为“domain logic”,这些domain logic应该最小化的依赖于DAO,而我们讨论的那些需要持久化操作参与的事务性逻辑,这里称之为“workflow methods”,这些“workflow methods”应该放在“business facade”,而不应该放在domain object里面。


其实现在讨论的就是从原来的标准:
引用

持久化是不是要放到domain object来做

变化为 那些工作属于workflow methods。
我的观点和Archie比较近,按照上一搁说法:前面的例子forum的例子其实还是type2比较好。因为forum。remove ()并不能算作一个workflow
0 请登录后投票
   发表时间:2005-03-24  
参与这个什么破贫血的domain object的讨论感觉很后悔,白白浪费了好几天的宝贵时间,绝大多数时间都浪费在统一术语上了, 最后才搞明白,原来Martin Fowler说的rich domain object其实就是我平时用的Hibernate的实体类,他的workflow business facade就是我平时用的xxxManager。建议大家有条件的还是把POEAA这本书搞来看看,好过在这里瞎猜。既然我的实际用法本来就是符合Martin的理论,我也就不再浪费时间在这个问题上纠缠了,撤了。

有兴趣的可以下载一下Hibernate的caveatemptor案例,看看那个model目录下面的代码,就是带有domain logic的domain object,只不过他没有抽象出来Business Facade,而是应用层代码直接调用DAO。
0 请登录后投票
   发表时间:2005-04-01  
纠正两点:

引用

我们一直提到的只有getter/setter的纯数据类,Martin Fowler有一个专用词汇,叫做Active Record


No, Active Record 的概念是:包含DomainObject的CRUD操作和部分domain logic.

另外,区分"workflow logic"和"domain logic"的准则应该由logic本身决定:

引用

紧密结合domain object的,可重用度很高的操作可能是domain logic,应该放在domain object里面;比较难重用的控制逻辑方法,特别是可跨越多个domain object的操作则放在business facade object里面。


而不是由是否依赖DAO或其事务性决定。事实上,Domain Object 无需关心DAO的具体实现。
0 请登录后投票
   发表时间:2006-09-18  
比如在一个domainObject里有用到Util方法的逻辑,而util方法是用到service的,那么算是什么逻辑?是否应该放在pojo里呢?
0 请登录后投票
   发表时间:2006-09-18  
lszone 写道
比如在一个domainObject里有用到Util方法的逻辑,而util方法是用到service的,那么算是什么逻辑?是否应该放在pojo里呢?


用到util应该不算业务!比如int型转成double型,过滤小数点等等!
0 请登录后投票
   发表时间:2006-09-19  
按照Eric的观点,一个应用应该分为4层:

1. 展现
2. 应用
3. 领域
4. 基础

一些辅助手段,例如数据库交互、消息、邮件等等,和业务没有直接关系的都划归基础结构层;

领域层包含Entity和Service两个比较大的概念,Entity可以理解为Domain Object(当然未必一定是贫血的),而Service就是一些控制逻辑,例如User与UserManager,Entity也可以有自己的行为,但是一些重要的逻辑一般放在Service中。

那么应用层是什么?它应该是一个粘合层,或者说成是Business Facade也可以,它仅仅只是用于调用Domain层和基础结构层中的Service,简单的实现一种协作的功能。

实际上对于Business Workflow而言,从业务内部流程来讲是从属于Domain层的,但从整个功能流程来看又是放在应用层面的,有些类似于嵌套的形式。
0 请登录后投票
论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics