mysql設置唯一約束引起的DuplicateKeyException的解決方案(保證提供服務的冪等性)


   DuplicateKeyException: 主鍵沖突異常

catch (DuplicateKeyException e) {
                        logger.info("重復請求。feeDetail={}", feeDetail.toString());
                    } 

 

最近項目中遇到一個問題,我們提供的一個對外的服務接口在數據庫網絡層報錯DuplicateKeyException,是由於業務方重復調用而業務本不該重復調用,但是我們管不了業務方只能自己調整。

      思路一:

          去掉設置的數據庫層的唯一約束,報錯是解決了但是會引起后面一系列的問題,肯定是行不通的。

      思路二:

          插入數據之前先判斷數據存在否,不存在再插入。但是高並發的情況下還是會存在問題,除非給數據加鎖,但是這樣復雜度更高並沒有必要。

      思路三:

          數據庫層面的問題從數據庫解決,可以用 insert ignore來解決,insert ignore就表示存在則插入不存在則忽略。

 

        思路三是很好的解決方法,但是遇到另一個問題,之前我插入之后都是把新生成的id返回回去,insert ignore則不管插入成功與否都會返回這個id,也就是業務邏輯那里並不能確定到底插入成功與否,插入的數據涉及到計算結果,為保證接口的冪等性,之前是在catch住DuplicateKeyException后又做了一些列的邏輯處理來保證接口冪等性。

        現在的問題由數據庫報錯變成了如何知道數據庫是否真正插入數據,這時候想到了ROW_COUNT()來判斷數據庫的執行結果。

        

       最后業務層根據返回的id是否是0就可以判斷數據是否真正插入,到這里問題也就解決了。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM