【問題解決】記一個“奇怪”的java.lang.NoSuchMethodError錯誤

問題現象

近期本人負責的一個SpringBoot模塊出現了java.lang.NoSuchMethodError報錯,問題情況如下:

  • A類提供了setJumpType(String type),B類調用A類的setJumpType(String type)報錯java.lang.NoSuchMethodError: com.xxx.A.setJumpType(Ljava/lang/String;)V
  • 在之前的發版的程序中,B類無變更,出現以上問題後,重新編譯B類問題解決。

常見該問題原因與解決方法

  • 方法不存在:變更實現
  • 方法簽名變更(一般博客中只關注到方法名與參數列表):修正方法名與參數列表

問題分析

  • 反編譯代碼和本地IDE源碼調試均無該報錯出現,方法是存在的
  • 檢查A類是否存在方法名稱和參數類型、數量變更,發現也沒問題
  • 使用javap -v命令分析,經比較之前編譯的與新編譯的B類調用A類的方法簽名中,返回值不同

處理方法

  • 原因確定是方法簽名的返回值發生變更
  • 既然這個類是個DTO對象,就可以不直接用對方的DTO,重寫一份放自己這邊解決該問題,類似的情況只能靠發版前,在測試環境自測功能是否正常,有問題及時發現與解決

問題總結

  • java.lang.NoSuchMethodError錯誤出現於方法不存在和簽名變更的情況
  • 方法簽名格式:類路徑.方法名(參數列表;)返回值類型
  • 返回值類型:void->V; 引用->L類路徑;
  • 方法簽名中除了類路徑變更會導致ClassNotFound異常外,(方法名、參數列表、返回值類型)發生變化都會引起NoSuchMethodError錯誤,可根據錯誤原因進行處理
  • 編譯的class文件中不僅包含自身源文件的編譯結果,還包含引用的類與方法的簽名信息,一旦簽名發生變更就會出現兼容性問題,可能造成NoSuchMethodError錯誤。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章