SpringMVC + Mybatis bug除錯 SQL正確,查資料庫卻返回NULL
阿新 • • 發佈:2022-05-04
今天碰到個bug,有點意思
背景是SpringMVC + Mybatis的一個專案,mapper檔案裡寫了一條sql 大概相當於 select a from tableA where b = "123" 這樣的級別
然後不管傳進去的是什麼 資料庫裡有沒有 都會返回null
第一反應是sql語句寫錯了,比如把1和小寫L弄混了之類的,傳給sql的引數裡有奇怪的空格等等
於是開啟debug log 拿到傳給sql的preparedStatement 和對應的引數
複製到console裡自己查了一下,可以執行,返回結果也正確,說明不是sql的問題
既然不是sql的問題,那隻好除錯一下程式碼了
既然preparedStatement sql能夠被打印出來,所以就不從業務邏輯加斷點了,直接定位到PreparedStatement類 找到execute方法,上個斷點開始單步
單步的時候發現了奇怪的現象,ide提示說原始碼和class檔案對應行不一致,單步除錯時程式碼在不同行之間亂跳,並且對我正在監視的變數報了一個類中不存在該變數的錯
所以懷疑是引用衝突了
接下來確認一下是不是引用了奇怪的類 ,用下面這個方法去定位一下PreparedStatement的位置
public static String where(final Class cls) { if (cls == null)throw new IllegalArgumentException("null input: cls"); URL result = null; final String clsAsResource = cls.getName().replace('.', '/').concat(".class"); final ProtectionDomain pd = cls.getProtectionDomain(); if (pd != null) { final CodeSource cs = pd.getCodeSource(); if (cs != null) result = cs.getLocation(); if (result != null) { if ("file".equals(result.getProtocol())) { try { if (result.toExternalForm().endsWith(".jar") || result.toExternalForm().endsWith(".zip")) result = new URL("jar:".concat(result.toExternalForm()) .concat("!/").concat(clsAsResource)); else if (new File(result.getFile()).isDirectory()) result = new URL(result, clsAsResource); } catch (MalformedURLException ignore) {} } } } if (result == null) { final ClassLoader clsLoader = cls.getClassLoader(); result = clsLoader != null ? clsLoader.getResource(clsAsResource) : ClassLoader.getSystemResource(clsAsResource); } return result.toString(); }
在IDEA裡 單步時按alt+F8 用where方法去查一下類,發現jvm沒有載入我認為的msql-java-connector-5.1.63 而是載入了一個內部類庫裡的java-connector,定位進去看了一下 確實是寫的有問題,原因找到了。
最後到maven依賴裡,開啟依賴樹,找到了載入這個自定義connector的pom條目,配置了<exclusions> ,然後重啟專案,解決。