把hibernate事务交给spring管理
来源:互联网 发布:防止刷短信验证码 php 编辑:程序博客网 时间:2024/05/29 19:11
一直在用spring管理hibernate的事务,但是一直没太搞清楚,今天梳理一下
版本问题
开始使用的spring 4.2.6.release和hibernate 5.2.5.final结果启动就报错 java.lang.NoSuchMethodError: org.hibernate.Session.getFlushMode()Lorg/hibernate/FlushMode;
有两种方案一种是把hibernate降到5.1,另一种是把spring升到5.3,最后我使用的是spring4.3.2.release和hibernate5.2.5.final.
注解方式
使用注解@Transactional
前,需要在xml配置
<!-- PlatformTransactionMnager --> <bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="dataSource" /> </bean> <!-- enable transaction annotation support --> <tx:annotation-driven transaction-manager="transactionManager" />
然后在需要启用事务的类或方法上加上@Transactional,在类上加对所有方法都有效,在单独方法上加只对这个方法有效.
@Transactional的参数
rollbackFor
定义回滚的抛出类型,默认是RuntimeException.class,设置成@Transactional(rollbackFor = Exception.class)
后,Exception和RuntimeException都会回滚,总之就是触发回滚的异常类型.在源码里是这样定义的Class<? extends Throwable>[] noRollbackFor() default {};
所以范围限制在Throwable的子类.
noRollbackFor
和rollbackFor相反,定义之后,该种异常不会触发回滚
isolation
事务隔离级别,默认是Isolation.DEFAULT,这里需要先介绍一下三种现象
1、脏读(dirty read):一个事务可以读取另一个尚未提交事务的修改数据。
2、非重复读(nonrepeatable read):在同一个事务中,同一个查询在T1时间读取某一行,在T2时间重新读取这一行时候,这一行的数据已经发生修改,可能被更新了(update),也可能被删除了(delete)。
3、幻像读(phantom read):在同一事务中,同一查询多次进行时候,由于其他插入操作(insert)的事务提交,导致每次返回不同的结果集。
不同级别对应的情况
级别和现象的关系
propagation
事务的传播类型
readOnly(默认 false)
如果readonly设置成true.当事务里有增删改操作时,会直接抛异常java.sql.SQLException: Connection is read-only. Queries leading to data modification are not allowed
timeout
事务的超时时间,当为默认值 TransactionDefinition.TIMEOUT_DEFAULT
时,会使用底层系统的默认超时时间.
transactionManager
一个特定事务的标识值,可以用来觉得目标transaction manager,匹配一个特定的 {@link org.springframework.transaction.PlatformTransactionManager}的bean definition.
xml方式
<bean id="transactionManager" class="org.springframework.orm.hibernate5.HibernateTransactionManager"> <property name="sessionFactory" ref="sessionFactory " /> </bean> <!-- 声明式容器事务管理 ,transaction-manager指定事务管理器为transactionManager --> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <!-- 定义方法的事务参数--> <tx:method name="add*" propagation="REQUIRED" /> <tx:method name="get*" propagation="REQUIRED" /> <tx:method name="del*" propagation="REQUIRED" /> <tx:method name="do*" propagation="REQUIRED" /> <tx:method name="*" read-only="true" /> </tx:attributes> </tx:advice> <aop:config expose-proxy="true"> <!-- 只对业务逻辑层实施事务 --> <aop:pointcut id="txPointcut" expression="execution(* com.xxx.ws.service..*.*(..))" /> <!-- Advisor定义,切入点和通知分别为txPointcut、txAdvice --> <aop:advisor pointcut-ref="txPointcut" advice-ref="txAdvice"/> </aop:config>
这样配置后所有service包下的类和方法都加上事务了.
dao的写法
在把事务交给spring管理后,dao里的查询方法也要采用一定的写法
1.采用sessionFactory.getCurrentSession();
的方式获取session
2.操作完成后不要关闭session
3.不要把异常catch掉,要往外抛,否则spring检测不到异常,就无法回滚
4.不要显示的调用Transaction的操作,会与spring的冲突
public int updateSql(String sql,Object...params) { Session session = sf.getCurrentSession(); try { NativeQuery nativeQuery = session.createNativeQuery(sql); for (int i = 0; i <params.length ; i++) { nativeQuery.setParameter(i,params[i]); } int num = nativeQuery.executeUpdate(); return num; } catch (Exception e) { throw new RuntimeException(e); }finally { } }
一些问题的处理
java.lang.IllegalStateException: Transaction not successfully started
不要在dao里显示的调用tx的操作,会出现上面的报错移除tx.commit()后修复.
必须要try-catch异常
有时候业务逻辑必须要把异常catch掉,这时候spring因为检测不到异常无法回滚,可以通过调用 TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
来手动回滚
org.hibernate.HibernateException: Could not obtain transaction-synchronized Session for current thread
没有配置spring管理的事务,或者配置没生效
- 把hibernate事务交给spring管理
- Hibernate将SessionFactory交给Spring来管理/Spring管理Hibernate事务的方式
- Spring 3.2.2 与Hibernate 4.3.5 集成(事务交给Spring管理)
- struts 交给spring管理
- spring管理hibernate事务
- Spring管理Hibernate事务
- Spring管理Hibernate事务
- Spring管理Hibernate事务
- Spring管理Hibernate事务
- 【j2ee spring】20、S2SH框架中,把struts2的action交给Spring管理有什么好处?
- 把状态栏交给application管理1
- 把本地jar交给maven管理
- struts2把action交给spring托管
- 将redis交给spring来管理
- Spring管理hibernate的事务的方法
- Spring管理Hibernate中的事务(2)
- Spring对Hibernate事务的管理
- Spring管理Hibernate事务出现异常处理
- 初识Python
- 砝码
- java关于javadoc的那些小技巧和你需要知道的地方(一)
- Linux--RH134---unit 8 ldap网络帐号
- IDEA spark 中scala的编译版本问题解决NoSuchMethodError (jvm )
- 把hibernate事务交给spring管理
- Socket 发送接收图像
- Arduino应用笔记(二)Matlab控制Arduino点亮一个LED灯
- HDU
- 前段html通过js拼接url?name=XXX&gender=XXX,然后调用jQuery的ajax,往后台传参数,前端alert参数是正常的,后端的参数是乱码
- nvidia jetson TX2配置caffe
- 关于html一些小操作(注:只是方便本人用的时候容易找,高手勿喷!)
- 南阳理工acm 苹果 (背包问题)
- 安卓沉浸式状态栏