問題說明
1. 網貸目前體系架構下,資金方進件審批結果,資金方放款結果,都需要跑批系統自動執行 拉取業務結果job來拉取,
該job執行間隔設置爲1分鐘
2. 在測試過程中發現,一段時間過後就發現跑批執行運來越慢,結果長期無法準時拉回網貸,查詢hades日誌發現
hades通過 order ex和loan ex 拉取5-6條省聯社結果數據,竟然要花到6分鐘
3. 重啓hades後,執行速度會有飛躍,從6分鐘馬上提升到300ms左右
4. 懷疑hades 有內存泄漏
Hades 內存泄漏排查過程
1.監控 vm上 hades 所在容器進程 內存增長情況 ,發現不到3小時,內存從2111420 增長到 3637660,如下:
2.登錄到hades 容器內部,執行top 監控內存變化 ,同樣發現 hades java進程 所用內存一直增長
根據以上判斷:判定 hades存在內存泄漏
3. 在hades 容器內安裝jdk-jmap 工具 抓取JVM heap 對象快照信息
4. 將data.hprof 文件導出到windows環境,安裝MAT工具來分析JVM 內存快照 圖表如下:可以基本判定javax.crypto.JceSecurity 對象存在內存泄漏
結論分析
1. 通過MAT分析,可以 確定是 矢隆 order ex,hades ex中對於報文的加解密模塊,存在內存泄漏,對於報文的每一次加
解密過程的內存都沒有釋放 ,百度後發現問題的根源是:java後端之加密碼模塊JceSecurity存在內存不釋放問題
JceSecurity的verificationResults 屬性上,在verificationResults 屬性中存在了過多的BouncyCastleProvider,隨着應用調用
加密的正在不斷的增多,未被GC回收。
對javax.crypto.JceSecurity進行反編譯查看代碼發現verificationResults 是static 類屬性,GC不會自動對其永久代進行回收
2. 矢隆ext 加解密代碼排查 ,在服務每次使用的時候都會重新創建一個BouncyCastleProvider用來進行初始化密鑰的工具類
3. 解決辦法 ,BouncyCastleProvider定義成單例
public static synchronized BouncyCastleProvider getInstance() {
if (bouncyCastleProvider == null) {
bouncyCastleProvider = new BouncyCastleProvider();
}
return bouncyCastleProvider;
}