2007-05-14
RichDomainObject的架构设计中,是否可以抛弃DAO?
关键字: domainmodel jpa dao
2、3年过去了,没想到最近Javaeye又有了对Domain设计的热贴,安耐不住,说说自己的想法。
2年前有过尝试RichDomainObject的设计,当时使用的hibernate2+SessionBean。
发现DomainObject必须要依赖Dao(一些业务逻辑执行前,需要对之前产生的DomainObject进行查询或汇总,根据结果判定执行逻辑);
同时为了查询的灵活,Service必须同时依赖Dao和DomainObject。
这样整个Server,实际上包括了4种东西:
Service、
ServiceDAO(ReadOnly)、
DomainObject、
DomainDAO(Read/Write)。
另外在Service层和各种Client端(Web/Swing/JavaApplication等)之间使用DTO传递数据。
注意DTO并不是与DomainObject一一对应的的PO无逻辑简化版本,相反DTO是与界面相关的,同一个DomainObject可能根据客户端(界面)的不同,有多个DTO与之对应。(演化到后来DTO变为了由集合、数组、String、Date、Integer等java基础类组合的一个数据结构,系统本身并不存在具体的DTO类,因为数据到界面后只为显示,并没有任何逻辑,无须用对象实现)。
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
技术在不断进化,JPA的出世,让我看到了一丝希望。
反思一下DAO出现的原始用意:
1)隔离数据库(JDBC)操作。[分层、弱化程序对数据库的直接依赖]
2)简化数据库间移植。[隔离具体数据库接口(SQL)细节,解除厂家邦定]
目前的JPA似乎完全满足了上面两种需求。
而且(JPA)是JAVA持久化API,不是JAVA数据库连接API(JDBC),其从概念上也是不依赖数据库的(完全有可能实现一个使用文件系统/XML进行持久化的JPA)。
同时,JPA本身也是一个隔离层,虽然目前作的不太完美,不过仍然给了你一个可以切换各种不同的JPA实现的机会。
现在看来我们是否可以抛弃DAO了呢?
让代码直接依赖java的标准api--JPA,就像依赖java.util一样?
2年前有过尝试RichDomainObject的设计,当时使用的hibernate2+SessionBean。
发现DomainObject必须要依赖Dao(一些业务逻辑执行前,需要对之前产生的DomainObject进行查询或汇总,根据结果判定执行逻辑);
同时为了查询的灵活,Service必须同时依赖Dao和DomainObject。
这样整个Server,实际上包括了4种东西:
Service、
ServiceDAO(ReadOnly)、
DomainObject、
DomainDAO(Read/Write)。
另外在Service层和各种Client端(Web/Swing/JavaApplication等)之间使用DTO传递数据。
注意DTO并不是与DomainObject一一对应的的PO无逻辑简化版本,相反DTO是与界面相关的,同一个DomainObject可能根据客户端(界面)的不同,有多个DTO与之对应。(演化到后来DTO变为了由集合、数组、String、Date、Integer等java基础类组合的一个数据结构,系统本身并不存在具体的DTO类,因为数据到界面后只为显示,并没有任何逻辑,无须用对象实现)。
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
技术在不断进化,JPA的出世,让我看到了一丝希望。
反思一下DAO出现的原始用意:
1)隔离数据库(JDBC)操作。[分层、弱化程序对数据库的直接依赖]
2)简化数据库间移植。[隔离具体数据库接口(SQL)细节,解除厂家邦定]
目前的JPA似乎完全满足了上面两种需求。
而且(JPA)是JAVA持久化API,不是JAVA数据库连接API(JDBC),其从概念上也是不依赖数据库的(完全有可能实现一个使用文件系统/XML进行持久化的JPA)。
同时,JPA本身也是一个隔离层,虽然目前作的不太完美,不过仍然给了你一个可以切换各种不同的JPA实现的机会。
现在看来我们是否可以抛弃DAO了呢?
让代码直接依赖java的标准api--JPA,就像依赖java.util一样?
评论
pig345
2007-05-17
xly_971223 写道
springside中OrderManager继承HibernateGenericDao<Order>的方式总感觉有点不对劲,如果OrderManager要用到多个dao不知道怎么实现?
呵呵,我记得有一条OO设计法则就是:不要继承工具类。
xly_971223
2007-05-16
引用
对于业务逻辑复杂的系统,这和我的思路不谋而合;但对于简单的CRUD操作缺显得比较繁琐,像SpringSide中那种统一封装Hibernate 可能更简单。
因此一个关键问题是项目和系统的复杂性。企业级软件往往70%以上的简单CRUD界面操作,加上30%的复杂业务逻辑。如果可能,一种策略是根据子系统或者模块的不同选择不同的设计策略。当然这有会引起复杂性,最后就根据自己项目的情况、人员水平进行权衡了。
因此一个关键问题是项目和系统的复杂性。企业级软件往往70%以上的简单CRUD界面操作,加上30%的复杂业务逻辑。如果可能,一种策略是根据子系统或者模块的不同选择不同的设计策略。当然这有会引起复杂性,最后就根据自己项目的情况、人员水平进行权衡了。
springside中OrderManager继承HibernateGenericDao<Order>的方式总感觉有点不对劲,如果OrderManager要用到多个dao不知道怎么实现?
pig345
2007-05-16
myace 写道
企业级软件往往70%以上的简单CRUD界面操作,加上30%的复杂业务逻辑。如果可能,一种策略是根据子系统或者模块的不同选择不同的设计。当然这有会引起复杂性,最后就根据自己项目的情况、人员水平进行权衡了。
比较同意这个策略,实际应用中应该不会引起复杂性,相反可能会使事情变得更简单。
不过我的经验上看,似乎没有什么对数据库的增、改、删操作不涉及到 业务逻辑/领域逻辑 的判定和计算的。
因此他们几乎都可以放到相应的DomainObject中去。
只有查询的操作是只与界面相关而不含有领域逻辑的,因此之前描述的设计中,为了优化性能并顾及查询灵活性,Service/action层是直接使用只读DAO查询DomainObject的。
myace
2007-05-16
pig345 写道
2、3年过去了,没想到最近Javaeye又有了对Domain设计的热贴,安耐不住,说说自己的想法。
2年前有过尝试RichDomainObject的设计,当时使用的hibernate2+SessionBean。
发现DomainObject必须要依赖Dao(一些业务逻辑执行前,需要对之前产生的DomainObject进行查询或汇总,根据结果判定执行逻辑);
同时为了查询的灵活,Service必须同时依赖Dao和DomainObject。
这样整个Server,实际上包括了4种东西:
Service、
ServiceDAO(ReadOnly)、
DomainObject、
DomainDAO(Read/Write)。
另外在Service层和各种Client端(Web/Swing/JavaApplication等)之间使用DTO传递数据。
注意DTO并不是与DomainObject一一对应的的PO无逻辑简化版本,相反DTO是与界面相关的,同一个DomainObject可能根据客户端(界面)的不同,有多个DTO与之对应。(演化到后来DTO变为了由集合、数组、String、Date、Integer等java基础类组合的一个数据结构,系统本身并不存在具体的DTO类,因为数据到界面后只为显示,并没有任何逻辑,无须用对象实现)。
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
技术在不断进化,JPA的出世,让我看到了一丝希望。
反思一下DAO出现的原始用意:
1)隔离数据库(JDBC)操作。[分层、弱化程序对数据库的直接依赖]
2)简化数据库间移植。[隔离具体数据库接口(SQL)细节,解除厂家邦定]
目前的JPA似乎完全满足了上面两种需求。
而且(JPA)是JAVA持久化API,不是JAVA数据库连接API(JDBC),其从概念上也是不依赖数据库的(完全有可能实现一个使用文件系统/XML进行持久化的JPA)。
同时,JPA本身也是一个隔离层,虽然目前作的不太完美,不过仍然给了你一个可以切换各种不同的JPA实现的机会。
现在看来我们是否可以抛弃DAO了呢?
让代码直接依赖java的标准api--JPA,就像依赖java.util一样?
2年前有过尝试RichDomainObject的设计,当时使用的hibernate2+SessionBean。
发现DomainObject必须要依赖Dao(一些业务逻辑执行前,需要对之前产生的DomainObject进行查询或汇总,根据结果判定执行逻辑);
同时为了查询的灵活,Service必须同时依赖Dao和DomainObject。
这样整个Server,实际上包括了4种东西:
Service、
ServiceDAO(ReadOnly)、
DomainObject、
DomainDAO(Read/Write)。
另外在Service层和各种Client端(Web/Swing/JavaApplication等)之间使用DTO传递数据。
注意DTO并不是与DomainObject一一对应的的PO无逻辑简化版本,相反DTO是与界面相关的,同一个DomainObject可能根据客户端(界面)的不同,有多个DTO与之对应。(演化到后来DTO变为了由集合、数组、String、Date、Integer等java基础类组合的一个数据结构,系统本身并不存在具体的DTO类,因为数据到界面后只为显示,并没有任何逻辑,无须用对象实现)。
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
技术在不断进化,JPA的出世,让我看到了一丝希望。
反思一下DAO出现的原始用意:
1)隔离数据库(JDBC)操作。[分层、弱化程序对数据库的直接依赖]
2)简化数据库间移植。[隔离具体数据库接口(SQL)细节,解除厂家邦定]
目前的JPA似乎完全满足了上面两种需求。
而且(JPA)是JAVA持久化API,不是JAVA数据库连接API(JDBC),其从概念上也是不依赖数据库的(完全有可能实现一个使用文件系统/XML进行持久化的JPA)。
同时,JPA本身也是一个隔离层,虽然目前作的不太完美,不过仍然给了你一个可以切换各种不同的JPA实现的机会。
现在看来我们是否可以抛弃DAO了呢?
让代码直接依赖java的标准api--JPA,就像依赖java.util一样?
对于业务逻辑复杂的系统,这和我的思路不谋而合;但对于简单的CRUD操作缺显得比较繁琐,像SpringSide中那种统一封装Hibernate 可能更简单。
因此一个关键问题是项目和系统的复杂性。企业级软件往往70%以上的简单CRUD界面操作,加上30%的复杂业务逻辑。如果可能,一种策略是根据子系统或者模块的不同选择不同的设计策略。当然这有会引起复杂性,最后就根据自己项目的情况、人员水平进行权衡了。
pig345
2007-05-15
xly_971223 写道
如果说Dao层可以抛弃 那末service层中的很多对单个Domain object的操作也可以加到DomainObject中
如果是领域相关的逻辑(而不是某个Client/界面独有的)本来就应该放到DomainObject中阿。
pig345
2007-05-15
partech 写道
关于JPA俺不太了解,但是不使用接口,只使用JPA是否能简明的表达如下的概念呢?
花时间看下,你的功力估计不用半天就可了解个大概。
因为与之前的hibernate原理上都很相似的。
而且目前也都是用hibernate作JPA provider
pig345
2007-05-15
partech 写道
多个DAO interface和implements,如果里面的方法和实现确实不同,那么是没办法减少这部分代码的,对么?
如果没理解错,你的“实现不同”多数是指针对不同的数据库产品的SQL不同吧,好像是jpa(或者之前的hibernate/toplink...)已经解决了这个问题。
其实仔细想想一般的BO+PO+DAO的设计里面,逻辑是分散在3种对象中的,BO 里有流程逻辑、PO 里是领域结构、一些复杂的情况中,DAO里面的SQL也体现了一部分业务计算逻辑。
将BO简化为Service(Action层),用来控制事务边界;业务逻辑和相关的PO结合形成DomainObject,并且DomainObject直接使用JPA(以及相关的JPQL查询语言),会保证所有领域逻辑都体现在对应的DomainObject中。
这样可能会带来DomainObject的复杂化,但是业务逻辑集中。
选择 复杂但少量(相对)精简的代码,还是 简单但大量(相对)臃肿的代码,这是一个问题阿!
xly_971223
2007-05-15
shaucle 写道
xly_971223 写道
如果说Dao层可以抛弃 那末service层中的很多对单个Domain object的操作也可以加到DomainObject中
俺还是认为Domain object瘦一点的好.
瘦一点的享受的服务通常更多,也更灵活.
如果要抛弃的话就来的彻底一些
当然我个人也不喜欢domain object带一些dao操作 那样的话客户端岂不是可以通过domain object调用dao方法了 就有点乱套了
shaucle
2007-05-15
xly_971223 写道
如果说Dao层可以抛弃 那末service层中的很多对单个Domain object的操作也可以加到DomainObject中
俺还是认为Domain object瘦一点的好.
瘦一点的享受的服务通常更多,也更灵活.
xly_971223
2007-05-14
如果说Dao层可以抛弃 那末service层中的很多对单个Domain object的操作也可以加到DomainObject中
shaucle
2007-05-14
dovecat 写道
等到JPA用的差不多了,大家又会觉得JPA也不是个好东东的说.
同意这个的说,不然事物怎么发展。
老马的理论还是很强的!
dovecat
2007-05-14
等到JPA用的差不多了,大家又会觉得JPA也不是个好东东的说.
partech
2007-05-14
pig345 写道
多了 Dao Interface / Dao Implements + 你自己写的Factory或Spring的配置。这许多的类不是很麻烦么?
主要是考虑当前的开发环境的进化, JPA 既然成为了标准API,我们能否信任他,就像信任java.util一样?
而且个人觉得现在大家似乎过分强调解偶,解偶也是有限度的,你不可能不依赖 java.lang java.util 来写程序吧。
主要是考虑当前的开发环境的进化, JPA 既然成为了标准API,我们能否信任他,就像信任java.util一样?
而且个人觉得现在大家似乎过分强调解偶,解偶也是有限度的,你不可能不依赖 java.lang java.util 来写程序吧。
多个DAO interface和implements,如果里面的方法和实现确实不同,那么是没办法减少这部分代码的,对么?
关于配置问题,可以使用一个Aspect搞定,因为可以查找到Dao interface和implements的关系。
关于JPA俺不太了解,但是不使用接口,只使用JPA是否能简明的表达如下的概念呢?
interface IProductFinder{
//查找客户在用产品
List findByCustomerCode(String code);
}
shaucle
2007-05-14
用了jpa就知道dao是多余的
其实不用也感觉得到这个东东就有点无中生有...
不过个人感觉jpa还可以简化(但未必是好事)
其实不用也感觉得到这个东东就有点无中生有...
不过个人感觉jpa还可以简化(但未必是好事)
pig345
2007-05-14
partech 写道
pig345 写道
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
敢问,如何繁琐的很呀?
多了 Dao Interface / Dao Implements + 你自己写的Factory或Spring的配置。这许多的类不是很麻烦么?
主要是考虑当前的开发环境的进化, JPA 既然成为了标准API,我们能否信任他,就像信任java.util一样?
而且个人觉得现在大家似乎过分强调解偶,解偶也是有限度的,你不可能不依赖 java.lang java.util 来写程序吧。
pig345
2007-05-14
还是需要澄清一下,虽然与http://www.javaeye.com/topic/56949讨论的都是Domain和DAO的关系问题,但是具体的实现选择根本不同。
大家在那里面讨论最多的似乎就是我所反对的(domain extends DAO 或 BO extends PO),而这里提出的是Domain直接使用JPA从而消除DAOinterface/DAOImpl !
大家在那里面讨论最多的似乎就是我所反对的(domain extends DAO 或 BO extends PO),而这里提出的是Domain直接使用JPA从而消除DAOinterface/DAOImpl !
partech
2007-05-14
pig345 写道
这样的架构下,感觉DAO的处理上实在是繁琐的很,时时有绕过它直接使用hibernate的冲动!
敢问,如何繁琐的很呀?
shaucle
2007-05-14
giscat 写道
pig345 写道
giscat 写道
如果你是老大,怎么玩都可以
当然包括自虐
当然包括自虐
技术讨论帖子,为什么要有嘲讽和人身攻击?请明确解释你的看法。
非常诚恳地声明一下:
并没有嘲讽和人身攻击嘛
切勿多愁善感,否则后果自负
本来就说得对嘛! 呵呵!
pig345
2007-05-14
lighter 写道
刚发完本帖,就看到了,还没看完。。。
无须争论,项目里实践下,毕竟省代码行数、省工作量、省测试量,才是硬道理。
shaucle
2007-05-14
pig345 写道
顺便说一下,本人极其不赞成使用BO(业务逻辑) extends PO(持久化)= DomainObject 的方式,虽然从代码上看,好像还算干净漂亮。
但是要知道,DomainObject是领域对象,他的extends应该体现业务逻辑对象之间的天然继承关系,而不要将这(在JAVA这种单继承静态类型语言里面是极其)宝贵的资源浪费到具体实现手段上!
但是要知道,DomainObject是领域对象,他的extends应该体现业务逻辑对象之间的天然继承关系,而不要将这(在JAVA这种单继承静态类型语言里面是极其)宝贵的资源浪费到具体实现手段上!
俺也这么认为,而且好像这种趋势越来越明显..
失血又怎么样,失血正好表明职责分明.
- 浏览: 8780 次
- 性别:

- 来自: 北京

- 详细资料
搜索本博客
最新评论
-
有感而发:JavaEE和ROR的 ...
樓主的話有道理!!
-- by java心如止水 -
有感而发:JavaEE和ROR的 ...
第一线的感想就是实在,这些抱怨看起来很亲切。不过,通过对比,我觉得它还是有优势。 ...
-- by liusong1111 -
有感而发:JavaEE和ROR的 ...
引用西西,说到搜索,javaeye就是典型,几乎搜索功能为0。 关于全文搜索对r ...
-- by wutao8818 -
有感而发:JavaEE和ROR的 ...
引用但是,“缺乏技术含量”的纯JSP和servlet很快,快到惊艳的程度。说点伤 ...
-- by 庄表伟 -
有感而发:JavaEE和ROR的 ...
引用不是人您就别在人堆里面瞎炫耀了哈哈,这句话比较有意思
-- by fujohnwang






评论排行榜