Dam*_*ien 5 jobs spring hibernate transactions web-applications
我有一个使用Spring 2.5和Hibernate 3的应用程序.
有一个带有表示层,服务层和DAO层的Web应用程序,以及一些共享相同服务和DAO层的Quartz作业.
使用@Transactional注释在不同的层中初始化事务,如下所示:

它引发了我在这里描述的一个问题:使用Spring 2.5从外部事务控制内部事务设置
我读了一些关于如何设置事务以将Spring和Hibernate连接在一起的内容.看起来推荐的方法是初始化服务层中的事务.
我不喜欢的是大多数事务的存在只是因为它们是hibernate正常工作所必需的.
当我真的需要一个调用多种服务方法的作业的事务时,似乎我没有选择继续从作业初始化事务.因此,将@Transactional注释从DAO移动到服务似乎没有任何区别.
您如何建议为此类应用程序设置事务?
我读了一些关于如何设置事务以将Spring和Hibernate连接在一起的内容.看起来推荐的方法是初始化服务层中的事务.
当然.事务划分应在服务层级别完成,而不是在DAO层级别完成:
我不喜欢的是大多数事务的存在只是因为它们是hibernate正常工作所必需的.
您应该详细说明这一部分,因为事务不是特定于Hibernate的.
当我真的需要一个调用多种服务方法的作业的事务时,似乎我没有选择继续从作业初始化事务.
如果要调用多个服务从作业层发起的事务中,与交易申报您的服务REQUIRED语义(默认值)和依赖于Spring事务传播(适用,除非你需要远程调用;在这种情况下,使用的EJB) .
因此,将@Transactional注释从DAO移动到服务似乎没有任何区别.
它确实有所作为,您在运行批不使事情变得不同,当需要从工作层发起交易的事实.
我热烈建议阅读第9章.事务管理.
(...)我的主要问题来自Hibernate.对不起,如果我不清楚.
没问题.只是当一个问题含糊不清时,你经常得到一个模糊的答案:)
Hibernate文档:"数据库事务绝不是可有可无的与数据库的所有通信都在事务中发生.".这就是为什么开发人员将DAO方法交易放在我的项目上的原因.
很抱歉,但上述声明只表示"与数据库的通信必须在事务中发生",仅此而已,并决定从何处开始交易由您自行决定(通常是服务层).如果你在DAO层面做到这一点,如果有什么MySuperService电话DaoFoo,并DaoBar和DaoBar失败?在这种情况下,您可能希望回滚所有更改,而不仅仅是那些更改DaoBar.因此需要控制工作单元开始的交易.
恕我直言,开发人员需要一些指导.
这是否意味着我的所有服务都应该是交易性的?即使我只是阅读数据?
首先,我建议阅读非事务性数据访问和自动提交模式(Sessions和事务的小兄弟)来澄清"只读事务"的内容.阅读整个页面是值得的,但让我引用这个特定的部分:
许多应用程序开发人员认为他们可以在事务之外与数据库通信.这显然是不可能的; 没有SQL语句可以发送到数据库事务之外的数据库.术语非事务性数据访问意味着没有明确的事务边界,没有系统事务,并且数据访问的行为是自动提交模式的行为.这并不意味着不涉及物理数据库事务.
一旦你完成上述链接,下一个建议的读数将是@Transactional只读标志陷阱.以下是相关部分:
(...)最重要的是,当您使用基于ORM的框架时,只读标志是无用的,在大多数情况下会被忽略.但是如果您仍然坚持使用它,请始终将传播模式设置为SUPPORTS,如清单9所示,因此不会启动任何事务:
清单9.使用只读和
SUPPORTS传播模式进行选择操作Run Code Online (Sandbox Code Playgroud)@Transactional(readOnly = true, propagation=Propagation.SUPPORTS) public TradeData getTrade(long tradeId) throws Exception { return em.find(TradeData.class, tradeId); }更好的是,
@Transactional在执行读取操作时完全避免使用 注释,如清单10所示:清单10.删除
@Transactionalselect操作的注释Run Code Online (Sandbox Code Playgroud)public TradeData getTrade(long tradeId) throws Exception { return em.find(TradeData.class, tradeId); }
| 归档时间: |
|
| 查看次数: |
1695 次 |
| 最近记录: |