[英]debugging Transactional annotation in Java Spring
如下所示更新現有代碼:
@Override
@Transactional
public void update(SomeObject someObj) throws BusinessServiceException {
...
someObjectRepository1.update(someObj);
someObjectRepository2.create(someObj);
//New code below:
someObjectRelatedService.doStuff(someObj); // <--new code
//Throws error, object does not exist in someObjectRepository2
}
這里的問題是someObjectRelatedService.doStuff需要someObjectRepository2的最新和最新版本-但是事務注釋阻止了這種情況的發生,它將在方法完全運行后更新存儲庫。 我能夠通過使用調試器並在兩者之間運行數據庫調用來進行驗證。
解決這種情況的最佳方法是什么? 是否僅在事務方法外部提取someObjectRelatedService調用?
本質上,您需要移動事務的邊界。 雖然可以手動刷新事務,但我不建議這樣做。
如果SomeObjectRepository2#create(...)
的語義允許,最簡單的解決方法是使用@Transactional(isolation = Propagation.REQUIRES_NEW)
注釋此方法。
如果這不可能,我建議進行以下較小的重新設計。 首先,我們使用一個方法創建一個新類,該方法應執行與所需數據相關的代碼:
@Component
public class NewClass {
final SomeObjectRepository2 someObjectRepository2;
@Autowired
public NewClass(final SomeObjectRepository2 someObjectRepository2) {
this.someObjectRepository2 = someObjectRepository2;
}
@Transactional(isolation = Propagation.REQUIRES_NEW) // enforces new transaction
public WhateverNeedsToBereturned newMethod(WhateverType someObject) {
return someObjectRepository2.create(someObj);
}
}
然后,我們重寫現有代碼以使用新類:
@Override
@Transactional
public void update(SomeObject someObj) throws BusinessServiceException {
...
someObjectRepository1.update(someObj);
newClassInstance.newMethod(someObj);
//New code below:
someObjectRelatedService.doStuff(someObj);
//Throws error, object does not exist in someObjectRepository2
}
請注意,您必須創建一個新類才能使其正常工作。 通過this
-reference進行的方法調用不被代理,因此@Transactional
注釋不生效。
還要注意, newClassInstance
相同的原因,必須通過DI容器注入newClassInstance
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.