我多次被问到这个问题并且现在很烦我。
我们有一个服务类,其中包含3个DAO方法,可以更新3个不同的表。 设计是这样的,所有三个表的更新应该是原子的。 我有3个线程分别调用我的服务类,并为每个DAO方法更新, 如何使用Spring事务或任何事务管理器将所有线程(操作)保留在单个事务下? 任何想法或指向文档? 谢谢!!
答案 0 :(得分:0)
服务方法应该是启动交易的方法
服务方法
public class Service{
// define dao1,dao2,dao3
@Transactional
public someMethod(){
dao1.someUpdate();
dao2.someUpdate();
dao3.someUpdate();
}
}
Dao1.class
public class Dao1{
@Transactional (propagation = Propagation.MANDATORY)
public someUpdate(){
}
}
类似于Dao2和Dao3
someUpdate()将使用Service.class的someMethod()启动的事务
答案 1 :(得分:0)
这可以通过将事务保持在线程级别来实现。但是,你需要所有这些线程之间的共享对象。此共享对象将跟踪所有此线程的状态,并在其中一个失败时通知它们。如果此线程收到失败通知,则他们自己可以抛出异常,并且它们的事务将被回滚。
示例代码 各个线程中的代码
@Transactional(rollbackFor = Exception.class)
public void saveData(Product product, ProductStatusObject productStatusObject) throws Exception {
productDao.persist(product);
if(product.getId() == 5) {
productStatusObject.updateCounter(false);
} else {
productStatusObject.updateCounter(true);
}
if(!productStatusObject.getStatus()) {
throw new Exception();
}
}
共享类中的代码 private final int totalThreads;
private int executedThreads = 0;
private Boolean finalStatus = true;
public ProductStatusObject(int totalThreads) {
this.totalThreads = totalThreads;
}
public synchronized void updateCounter(Boolean threadStatus) throws InterruptedException {
executedThreads ++;
if(!threadStatus) {
this.finalStatus = false;
}
if(totalThreads == executedThreads) {
notifyAll();
} else {
wait();
}
}
public synchronized Boolean getStatus() {
return finalStatus;
}
这里的失败条件是,如果任何线程正在保存id为5的数据,则所有线程都将回滚其代码。否则一切都会成功