问题描述
我们有一个春季交易回滚问题,回滚似乎不起作用.
在用@Transactional
注释的服务层方法中,我调用了三个不同的DAOImpl
类以插入3条记录.
中间的插入从第4个表进行get操作以填充描述字段,但此操作失败.我希望第一个插入回滚,但是似乎没有发生.
几点:
We have a Spring Transaction rollback issues, where rollback doesn't seems to be working.
Within my service layer method which is annotated with @Transactional
I call three different DAOImpl
classes to insert 3 records.
The middle insert do a get from a 4th table to populate a description field but this get failed. I expect the first insert to rollback but it doesn't seems to be happening.
Few Points:
- 'Get'方法引发运行时异常
- 我们正在使用
applicationContext.xml
中定义的org.springframework.jdbc.datasource.DataSourceTransactionManager
和MySQL datasource
.在Beans.xml
中创建Bean,然后将其导入ApplicationContext.xml
- 在
DAO
层
中没有 - 我们在
applicationContext.xml
中再次使用了 - 我们正在使用Spring 3.1
@Transactional
批注<tx:annotation-driven transaction-manager="transactionManager"/>
- The 'Get' method throws a Runtime Exception
- We are using
org.springframework.jdbc.datasource.DataSourceTransactionManager
andMySQL datasource
defined inapplicationContext.xml
. Beans are created inBeans.xml
which is imported intoApplicationContext.xml
- No
@Transactional
annotation inDAO
layer - We have used
<tx:annotation-driven transaction-manager="transactionManager"/>
again inapplicationContext.xml
- We are using Spring 3.1
更新:
代码段....
Service Class-这有点类似于我的....我在使用@Autowired和不使用@Autowired的情况下进行了测试.在服务类中调用事务启用方法.
Service Class- This is somthing similar to what I have .... I tested with and without @Autowired. The transaction enable method is called within the service class.
public class CustomerService {
//@Autowired
CustomerOrderDAO customerOrderDAOImpl;
//@Autowired
CustomerItemDAO customerItemDAOImpl;
//@Autowired
CustomerPromotionDAO customerPromotionDAOImpl;
//@Autowired
PromotionDAO promotionDAOImpl;
//other variables
public CustomerOrder handleIncomingOrders(CustomerOrder customerOrder) {
try {
saveOrderDetails(customerOrder);
.....
return customerOrder;
} catch (Exception e) //TO-DO catch proper exception
{
//Send error response
.......
return customerOrder;
}
}
@Transactional
public void saveOrderDetails(CustomerOrder customerOrder) throws Exception {
customerOrderDAOImpl.create(customerOrder);
....
while (promotionsIterator.hasNext()) {
customerPromotion.setPromotionName(promotionDAOImpl.getName(customerOrder.getPromotionId));
customerPromotionDAOImpl.create(customerPromotion);
}
......
while (customerItemIterator.hasNext()) {
customerItemDAOImpl.create(customerItem);
}
}
}
有什么主意吗?谢谢.
Any idea?Thanks.
推荐答案
@Transactional
的默认行为是在对象周围添加了代理的事务性行为(在您的示例中为CustomerService
).来自参考文档(向下滚动):
The default behaviour of @Transactional
is that transactional behaviour is added with a proxy around the object (the CustomerService
in your example). From the reference docs (scroll down):
在您的示例中,对handlingIncomingOrders()
的外部调用通过代理,并命中了目标对象(CustomerService
的实例).但是,对saveOrderDetails()
的后续调用是目标对象内部的常规方法调用,因此永远不会调用代理中的事务行为.但是,如果saveOrderDetails()
是从另一个类中调用的,则您会发现事务行为将按预期进行.
In your example, an external call to the handlingIncomingOrders()
passes through the proxy and hits the target object (an instance of the CustomerService
). However, the subsequent call to saveOrderDetails()
is a normal method call inside the target object, thus the transactional behaviour in the proxy is never invoked. However, if the saveOrderDetails()
was called from another class, you will find that the transactional behaviour will work as expected.
这篇关于春季交易不会回滚的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!