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-Plus 中 Mapper 重載踩坑指南

        共 2648字,需瀏覽 6分鐘

         ·

        2021-08-23 02:29

        前言

        近期在 Mapper 中寫了個(gè)方法重載,然后死活查不到正確結(jié)果,最終靈機(jī)一動(dòng),想到是不是因?yàn)橹剌d,然后我 Shift + F6 把重載方法名字改了一下!結(jié)果,顯而易見,重載的那個(gè)方法也一塊改了。再次躺坑!

        1

        背景

        以下為模式測試數(shù)據(jù)

        • MySQL 表
        • Mapper

        如果看到這里,已經(jīng)發(fā)現(xiàn)了問題,并知道原因,那可以直接跳過,進(jìn)行三連即可。

        當(dāng)然,在 Mapper.xml 這么寫,會提示錯(cuò)誤(插件功能)

        • Junit

        執(zhí)行結(jié)果是:

        sum=1500 sumWithTime=1500

        這就神奇了,沒有報(bào)錯(cuò),結(jié)果竟然是相同的。

        版本依賴

        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.1.2</version>
        </dependency>

        mybatis-plus-boot-starter 3.1.2 對應(yīng)的是 mybatis:3.5.1 和 mybatis-spring:2.0.1

        3

        深入排查

        MyBatis-Plus

        兩個(gè)結(jié)果相同,那就斷點(diǎn)斷到第二個(gè)上面,debug 進(jìn)去,看看執(zhí)行過程。

        F7 進(jìn)入!這里直接進(jìn)到 com.baomidou.mybatisplus.core.override.MybatisMapperProxy#invoke

        這里都是 mybatis-plus 的代理。

        進(jìn)入跟進(jìn),進(jìn)入到 com.baomidou.mybatisplus.core.override.MybatisMapperMethod#execute

        這里相當(dāng)于執(zhí)行

        Object result = sqlSession.selectOne("com.liuzhihang.demo.mapper.TransOrderMapper.sumOrderAmount", param);

        后面就是進(jìn)入 Mybatis 的環(huán)節(jié)了。

        在這里會進(jìn)入 Mybatis 的 slectList 方法(org.apache.ibatis.session.defaults.DefaultSqlSession#selectList)。

        從 configuration 中生成所有的 mappedStatements,然后從 statements 中獲取根據(jù) id,也就是方法的全路徑,獲取當(dāng)前的 statements。

        先看看 mappedStatements 里面都有啥?

        1. mappedStatements 是一個(gè) Map 結(jié)構(gòu)!
        2. 其中 key 是方法名,value 是一個(gè) MappedStatement

        所以這里的意思是根據(jù)方法的全路徑名稱,獲取一個(gè) MappedStatement, 而 com.liuzhihang.demo.mapper.TransOrderMapper.sumOrderAmount 在這里面只有一個(gè)。

        所以最終執(zhí)行的 sql 是 select ifnull(sum(order_amount),0) from trans_order where user_id = ? ;。這也是為什么兩個(gè)方法執(zhí)行的結(jié)果是相同的了。

        究其原因,則是因?yàn)?configuration 中就沒有重載方法的 MappedStatement

        而根本原因則是在 com.baomidou.mybatisplus.core.MybatisConfiguration#addMappedStatement 中寫了一段代碼!

        如果已經(jīng)存在,則直接忽略,同時(shí)會打印日志。

        mapper[xxx] is ignored, because it exists, maybe from xml file

        MyBatis

        那如果使用原生 MyBatis 呢?

        其實(shí)會在啟動(dòng)階段就報(bào)錯(cuò),服務(wù)直接啟動(dòng)失敗。

        其中異常是:

        java.lang.IllegalArgumentException: Mapped Statements collection already contains value xxx

        進(jìn)入源碼,org.apache.ibatis.session.Configuration#addMappedStatement

        在這里會創(chuàng)建 mappedStatements,調(diào)用的是 Map 的 put 方法。

        Configuration.StrictMap#put 繼承了 HashMap 具體內(nèi)容不細(xì)看。

        其中 key 的結(jié)構(gòu)是方法的方法全路徑。比如 com.liuzhihang.demo.mapper.TransOrderMapper.sumOrderAmount

        而第二次重載方法,來的時(shí)候就會拋出異常。

        3

        總結(jié)

        1. 在 MyBatis-Plus 中 Mapper 重載并不會出現(xiàn)異常,但是查詢結(jié)果都是相同的。因?yàn)?MyBatis-Plus 的 MybatisConfiguration 繼承重寫了 MyBatis Configuration 的 addMappedStatement 方法。
        2. 在 MyBatis-Plus 中發(fā)現(xiàn)該 MappedStatement 已經(jīng)存在,則不進(jìn)行添加。
        3. 而在 MyBatis 中如果 MappedStatement 如果 key 存在,則直接拋出異常,服務(wù)啟動(dòng)失敗。

        以上就是我經(jīng)歷的一個(gè)小坑,也是因?yàn)閭€(gè)人圖省事,寫了個(gè)重載。雖然記得不能重載,但是看啟動(dòng)沒問題,就覺得 ok。


        - <End /> -




        歷史文章 | 相關(guān)推薦



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

        手機(jī)掃一掃分享

        分享
        舉報(bào)
        評論
        圖片
        表情
        推薦
        點(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>
            骚虎视频www网站 | 97自拍网 | 欧美日穴视频 | 美国一级黄色电影 | 娇妻与欧美黑人3p高清视频 | 丰满岳乱在线观看视频国产 | 嫩草香蕉在线91一二三区 | 国产人妻精品一区二区三水牛影视 | 玖玖精品网 | 自由日本语亚洲人高潮 |