1. <strong id="7actg"></strong>
    2. <table id="7actg"></table>

    3. <address id="7actg"></address>
      <address id="7actg"></address>
      1. <object id="7actg"><tt id="7actg"></tt></object>

        公司新來小伙,把 MyBatis 替換成 MyBatis-Plus,上線后被開了.....

        共 6125字,需瀏覽 13分鐘

         ·

        2024-05-25 10:30

        來源:程序員江小北

        ?? 歡迎加入小哈的星球 ,你將獲得: 專屬的項(xiàng)目實(shí)戰(zhàn) / Java 學(xué)習(xí)路線 / 一對一提問 / 學(xué)習(xí)打卡 /  每月贈書


        新項(xiàng)目:仿小紅書(微服務(wù)架構(gòu))正在更新中... , 全棧前后端分離博客項(xiàng)目 2.0 版本完結(jié)啦, 演示鏈接http://116.62.199.48/ 。全程手摸手,后端 + 前端全棧開發(fā),從 0 到 1 講解每個功能點(diǎn)開發(fā)步驟,1v1 答疑,直到項(xiàng)目上線。目前已更新了261小節(jié),累計(jì)43w+字,講解圖:1806張,還在持續(xù)爆肝中.. 后續(xù)還會上新更多項(xiàng)目,目標(biāo)是將Java領(lǐng)域典型的項(xiàng)目都整一波,如秒殺系統(tǒng), 在線商城, IM即時通訊,Spring Cloud Alibaba 等等,戳我加入學(xué)習(xí),已有1400+小伙伴加入(早鳥價超低)


        背景簡介

        在一個老項(xiàng)目中,數(shù)據(jù)庫采用的是 MySQL 5.7.36,ORM 框架使用的是 MyBatis 3.5.0,而 mysql-connector-java 的版本是 5.1.26。

        有一天,一個精力充沛、充滿折騰精神的年輕人加入了項(xiàng)目。

        他覺得 MyBatis 的使用不夠簡單,需要寫的代碼比較多,因此認(rèn)為有必要將其替換為 MyBatis-Plus。

        MyBatis-Plus 替換 MyBatis

        首先,我們準(zhǔn)備了一張名為 tbl_order 的表,并初始化了其中的兩條數(shù)據(jù)。

        DROP TABLE IF EXISTS `tbl_order`;
        CREATE TABLE `tbl_order`  (
          `id` bigint(0) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '自增主鍵',
          `order_no` varchar(50) NOT NULL COMMENT '訂單號',
          `pay_time` datetime(3) DEFAULT NULL COMMENT '付款時間',
          `created_at` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) COMMENT '創(chuàng)建時間',
          `updated_at` datetime(3) NOT NULL DEFAULT CURRENT_TIMESTAMP(3) ON UPDATE CURRENT_TIMESTAMP(3) COMMENT '最終修改時間',
          PRIMARY KEY (`id`) USING BTREE
        ) ENGINE = InnoDB COMMENT = '訂單';
         
        INSERT INTO `tbl_order` VALUES (1, '123456''2024-02-21 18:38:32.000''2024-02-21 18:37:34.000''2024-02-21 18:40:01.720');
        INSERT INTO `tbl_order` VALUES (2, '654321''2024-02-21 19:33:32.000','2024-02-21 19:32:12.020''2024-02-21 19:34:03.727');

        為了簡化演示,我們直接使用 MyBatis-Plus 構(gòu)建了一個示例 demo,以此來模擬這位年輕人的替換過程。

        我們只是簡單地將 MyBatis-Plus 替換了 MyBatis,而其他組件的版本保持不變。

        我們使用的 MyBatis-Plus 版本是這位年輕人引用的版本:3.1.1,

        mysql-connector-java 的版本保持不變,仍然是 5.1.26。

        示例代碼:play_it_safe

        然后,運(yùn)行 com.qsl.OrderTest#orderListAllTest,卻遇到了報(bào)錯,異常信息如下所示:

        請注意 Caused by 部分。

        圖片

        不支持的轉(zhuǎn)換類型:java.time.LocalDateTime

        是誰不支持呢?是 mysql-connector-java 不支持!

        那么,哪個版本的 mysql-connector-java 支持呢?

        ?

        答案是:5.1.37

        ?

        圖片

        升級 mysql-connector-java

        我們將 mysql-connector-java 升級到 5.1.37,然后再次執(zhí)行 com.qsl.OrderTest#orderListAllTest。

        圖片

        這次不再報(bào)異常,并且查詢結(jié)果也是正確的。

        看起來,MyBatis-Plus 替換 MyBatis 的任務(wù)完成了。

        這一切都如此順利,讓人有些懷疑。

        圖片

        讓我們再回頭看看之前提到的異常:

        Conversion not supported for type java.time.LocalDateTime

        在替換 MyBatis 之前并沒有這個異常,但在替換之后就出現(xiàn)了這個異常,這難道不是 MyBatis-Plus 的問題嗎?

        那么如何找到這個異常的根本原因呢?

        其實(shí)很簡單,直接從異常堆棧入手。

        圖片

        點(diǎn)擊后,你會發(fā)現(xiàn)代碼非常簡單。

        圖片

        這么簡單的代碼怎么會有問題呢?

        大家請注意圖中左上角的 MyBatis 版本,是 3.5.1,而不是最初的 3.5.0。

        可能有人會問:「既然替換成了 MyBatis-Plus,為什么還有 Mybatis 的存在?」

        這個問題問得確實(shí)好,我只想給你個大嘴巴。

        圖片

        現(xiàn)在讓我們看一下 MyBatis-Plus 的官方說明。

        圖片

        既然基于 Mybatis 3.5.0 沒有拋出異常,而基于 3.5.1 卻拋出了異常。

        ?

        “LocalDateTimeTypeHandler” 在 3.5.1 中肯定進(jìn)行了調(diào)整

        ?

        那我們來看看調(diào)整了什么?

        圖片

        看出什么了嗎?

        MyBatis 3.5.0 會處理 LocalDateTime 類型的轉(zhuǎn)換(將 java.sql.Timestamp 轉(zhuǎn)換成 java.time.LocalDateTime)。

        然而,注意了啊,最關(guān)鍵的地方來了!

        從 MyBatis 3.5.1 開始,不再處理 LocalDateTime(還包括:LocalDate、LocalTime)類型的轉(zhuǎn)換,而是交由 JDBC 組件,也就是 mysql-connector-java 來實(shí)現(xiàn)。

        而巧的是:

        ?

        mysql-connector-java 5.1.26 不支持類型 LocalDateTime。

        ?

        圖片

        那么它支持哪些類型呢?

        我們同樣從異常堆棧入手。

        圖片

        點(diǎn)擊后,可以看到下圖。

        圖片

        往上滑動鼠標(biāo),就可以看到支持的類型。

        確實(shí)沒有 LocalDateTime、LocalDate 和 LocalTime。

        ?

        mysql-connector-java 5.1.37 開始支持 LocalDateTime、LocalDate 和 LocalTime,前面已經(jīng)介紹過了,不再贅述。

        ?

        總結(jié)異常根本原因:

        ?

        MyBatis 3.5.1 開始不再處理 LocalDateTime、LocalDate 和 LocalTime 的轉(zhuǎn)換,而 mysql-connector-java 5.1.37 之前都不支持這些類型。

        ?

        搞清楚了這個異常的來龍去脈,順理成章的感覺是不是又回來了?

        暴風(fēng)雨來臨

        版本上線不到兩天,該來的終究還是來了。

        我們往表 tbl_order 中插入了一條記錄:

        INSERT INTO tbl_order 
        VALUES (3, 'asdfgh', NULL, '2024-02-21 20:01:31.111''2024-02-21 20:02:56.764');

        然后再次執(zhí)行 com.qsl.OrderTest#orderListAllTest。

        圖片

        此時我就想問這位年輕人:爽不爽?

        圖片

        遇到了異常,那就找出原因。

        同樣從異常堆棧入手。

        圖片

        看出什么了嗎?

        如果 getTimestamp(columnIndex) 得到的是 NULL,那不就是 NullPointerException?這也太不嚴(yán)謹(jǐn)了吧?

        修復(fù)問題是當(dāng)務(wù)之急,先看哪個版本進(jìn)行了修復(fù)?

        圖片

        將 mysql-connector-java 升級到 5.1.42。

        圖片

        問題得以修復(fù)。

        ?

        經(jīng)過這一次事件,這位年輕人似乎成長了許多,但眼中的光卻黯淡了不少。

        ?

        Mybatis-Plus 的問題

        無意中我看到了這個 issue-1114,是不是和我們之前分析的 “Conversion not supported for type java.time.LocalDateTime” 是同一個問題?

        只是我們使用的數(shù)據(jù)庫連接池是默認(rèn)的 HikariCP 而非 Druid。

        結(jié)合 druid/issues/3302,如果使用 Druid 作為數(shù)據(jù)庫連接池,出現(xiàn)的異??赡芘c我們之前分析的確實(shí)不同。

        因此,大家需要根據(jù)自己的實(shí)際情況進(jìn)行分析,但對異常的分析方法是通用的。

        總結(jié)

        關(guān)于組件的升級或舊代碼的調(diào)整,都可能引發(fā)連鎖反應(yīng),影響重大。

        我的觀點(diǎn)是:

        ?

        能不動就不要動,改好沒功勞,改壞要背鍋,吃力不討好,又不是必須要改。

        ?

        如果不得不改,那就需要全面的測試。

        ?? 歡迎加入小哈的星球 ,你將獲得: 專屬的項(xiàng)目實(shí)戰(zhàn) / Java 學(xué)習(xí)路線 / 一對一提問 / 學(xué)習(xí)打卡 /  每月贈書


        新項(xiàng)目:仿小紅書(微服務(wù)架構(gòu))正在更新中... , 全棧前后端分離博客項(xiàng)目 2.0 版本完結(jié)啦, 演示鏈接http://116.62.199.48/ 。全程手摸手,后端 + 前端全棧開發(fā),從 0 到 1 講解每個功能點(diǎn)開發(fā)步驟,1v1 答疑,直到項(xiàng)目上線。目前已更新了261小節(jié),累計(jì)43w+字,講解圖:1806張,還在持續(xù)爆肝中.. 后續(xù)還會上新更多項(xiàng)目,目標(biāo)是將Java領(lǐng)域典型的項(xiàng)目都整一波,如秒殺系統(tǒng), 在線商城, IM即時通訊,Spring Cloud Alibaba 等等,戳我加入學(xué)習(xí),已有1400+小伙伴加入(早鳥價超低)



            
               

        1. 我的私密學(xué)習(xí)小圈子~

        2. 面試官:Spring 為什么不支持 static 字段的注入?

        3. 企業(yè)級消息推送架構(gòu)設(shè)計(jì),太強(qiáng)了!

        4. @Transactional 中使用線程鎖導(dǎo)致了鎖失效,驚了!

        最近面試BAT,整理一份面試資料Java面試BATJ通關(guān)手冊,覆蓋了Java核心技術(shù)、JVM、Java并發(fā)、SSM、微服務(wù)、數(shù)據(jù)庫、數(shù)據(jù)結(jié)構(gòu)等等。

        獲取方式:點(diǎn)“在看”,關(guān)注公眾號并回復(fù) Java 領(lǐng)取,更多內(nèi)容陸續(xù)奉上。

        PS:因公眾號平臺更改了推送規(guī)則,如果不想錯過內(nèi)容,記得讀完點(diǎn)一下在看,加個星標(biāo),這樣每次新文章推送才會第一時間出現(xiàn)在你的訂閱列表里。

        點(diǎn)“在看”支持小哈呀,謝謝啦

        瀏覽 532
        1點(diǎn)贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        評論
        圖片
        表情
        推薦
        1點(diǎn)贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        1. <strong id="7actg"></strong>
        2. <table id="7actg"></table>

        3. <address id="7actg"></address>
          <address id="7actg"></address>
          1. <object id="7actg"><tt id="7actg"></tt></object>
            吴梦梦av一区二区三区 | 图片区小说区激情区偷拍区 | 我天天干天天干屄 | 日韩一区不卡 | 小骚货干死你视频 | 爆乳极品自慰91久久久久 | 浓毛少妇泬18p | 免费人成视频在线 | 日本草逼网 | 日韩18|