[英]how to catch OptimisticLockException in web layer
我遇到一個問題,就是當EJB層引發OptimisticLockException時,如何在Web層(.war代碼)中捕獲它。
我們使用的是JEE5,GlassFishV2.1和JPA(以及TopLinks)和容器托管事務,但是當臟讀是由於另一個並發用戶在同一實體上的交易而發生的時,會在戰爭層上產生Transaction.RollBackException,這實際上是導致但是我無法在戰爭方面趕上OptimisticLockException。
在ejb端使用em.flush,然后我們可以捕獲一些自定義異常並將其引發戰爭。 但是我認為em.flush會刷新所有數據庫,這是否是一項昂貴的操作?
try{
//some enitity
em.flush()
}
catch(OptimisticLockException ole){
throw ole;
}
我的觀點是不要調用em.flush,因為在90%的情況下,將不會出現OptimisticLockException,並在.war中捕獲EJBException,然后重試。 有更好的選擇嗎?
試試{//一些代碼} catch(EJBException ex){
if (ex.getCausedByException().getCause().toString().
indexOf("javax.transaction.RollbackException")!= -1){
// do work
}
}
}
你可以做。 flush()從技術上講並不是昂貴的操作,因為它不再需要通過提交來完成寫入數據庫的工作,因此沒有額外的數據庫訪問權限,也不會“刷新所有數據庫”。 盡管flush()確實有一些開銷,但是更改將被計算兩次,一次是刷新,一次是提交,一次是提交。 根據更改策略和托管對象的數量,這確實需要一定的成本。 刷新還需要將受管對象放回跟蹤的受管狀態,這也要付出一些代價,但與數據庫訪問成本相比通常較小。
請注意,在提交期間可能會發生除鎖定錯誤以外的其他錯誤,因此,即使您使用刷新來捕獲鎖定錯誤,您在戰爭中仍然需要代碼來處理其他失敗原因,因此不要使用刷新,而只是使用一般事務失敗的錯誤處理可能是最好的解決方案。 如果要對鎖定錯誤進行特殊處理,則應該能夠按原因查找異常,但是在重試該操作時要小心,因為鎖定是有原因的,因此應該將錯誤報告給用戶並讓他們重試其操作。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.