我成功地将这个注解用于一个 Dao 类。回滚适用于测试。
但现在我需要回滚真实代码,而不仅仅是测试。有用于测试的特殊注释。但是哪些注解是针对非测试代码的呢?对我来说这是一个很大的问题。我已经为此花了一天时间。官方文档不符合我的需求。
class MyClass { // this does not make rollback! And record appears in DB.
EmployeeDaoInterface employeeDao;
public MyClass() {
ApplicationContext context = new ClassPathXmlApplicationContext(
new String[] { "HibernateDaoBeans.xml" });
employeeDao = (IEmployeeDao) context.getBean("employeeDao");
}
@Transactional(rollbackFor={Exception.class})
public void doInsert( Employee newEmp ) throws Exception {
employeeDao.insertEmployee(newEmp);
throw new RuntimeException();
}
}
员工道是
@Transactional
public class EmployeeDao implements IEmployeeDao {
private SessionFactory sessionFactory;
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
public void insertEmployee(Employee emp) {
sessionFactory.getCurrentSession().save(emp);
}
}
这是一个注释工作良好的测试:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { "/HibernateDaoBeans.xml" })
@TransactionConfiguration(transactionManager = "txManager", defaultRollback = true)
@Transactional
public class EmployeeDaoTest {
@Autowired
EmployeeDaoInterface empDao;
@Test
public void insert_record() {
...
assertTrue(empDao.insertEmployee(newEmp));
}
HibernateDaoBeans.xml
...
<bean id="employeeDao" class="Hibernate.EmployeeDao">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
<tx:annotation-driven transaction-manager="txManager"/>
<bean id="txManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
...
**是的,我回滚了交易。我刚刚为服务添加了 BEAN...然后注释 @Transactional 开始工作:-) **
<bean id="service" class="main.MyClass">
<property name="employeeDao" ref="employeeDao" />
</bean>
谢谢大家,俄罗斯不会忘记你的!
只需从标记为 @Transactional
的方法中抛出任何 RuntimeException
。
默认情况下,所有 RuntimeException
的回滚事务都不会,而检查的异常则不会。这是 EJB 的遗产。您可以使用 rollbackFor()
和 noRollbackFor()
注释参数进行配置:
@Transactional(rollbackFor=Exception.class)
这将在抛出任何异常后回滚事务。
或以编程方式
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
您可以从要回滚的方法中抛出未经检查的异常。这将被 spring 检测到,并且您的事务将被标记为仅回滚。
我假设你在这里使用 Spring。我假设您在测试中引用的注释是基于弹簧测试的注释。
向 Spring Framework 的事务基础结构指示事务的工作要回滚的推荐方法是从当前在事务上下文中执行的代码中抛出异常。
并注意:
请注意,Spring 框架的事务基础结构代码默认情况下只会在运行时、未经检查的异常情况下将事务标记为回滚;也就是说,当抛出的异常是 RuntimeException 的实例或子类时。
对我来说 rollbackFor 是不够的,所以我不得不把它放进去,它按预期工作:
@Transactional(propagation = Propagation.REQUIRED, readOnly = false, rollbackFor = Exception.class)
我希望它有帮助:-)
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
下面你帮助
@Transactional
注释。否则,每个 DAO 调用都会在您在服务中引发异常之前启动并提交新事务。底线是:异常必须离开(转义)标记为@Transactional
的方法。org.springframework.orm.hibernate3.HibernateTransactionManager
?如果启用org.springframework.transaction
记录器,它会显示什么有趣的东西吗?