<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          再見,MybatisPlus!

          共 6554字,需瀏覽 14分鐘

           ·

          2021-08-12 12:01

          原文:https://juejin.cn/post/6886019929519177735

          使用 fluent mybatis 可以不用寫具體的 xml 文件,通過 java api 可以構(gòu)造出比較復雜的業(yè)務(wù) sql 語句,做到代碼邏輯和 sql 邏輯的合一。

          使用 fluent mybatis 可以不用寫具體的 xml 文件,通過 java api 可以構(gòu)造出比較復雜的業(yè)務(wù) sql 語句,做到代碼邏輯和 sql 邏輯的合一。不再需要在 Dao 中組裝查詢或更新操作,在 xml 或 mapper 中再組裝參數(shù)。那對比原生 Mybatis, Mybatis Plus 或者其他框架,F(xiàn)luentMybatis 提供了哪些便利呢?

          我們通過一個比較典型的業(yè)務(wù)需求來具體實現(xiàn)和對比下,假如有學生成績表結(jié)構(gòu)如下:

          create table `student_score`
          (
          id bigint auto_increment comment '主鍵ID' primary key,
          student_id bigint not null comment '學號',
          gender_man tinyint default 0 not null comment '性別, 0:女; 1:男',
          school_term int null comment '學期',
          subject varchar(30) null comment '學科',
          score int null comment '成績',
          gmt_create datetime not null comment '記錄創(chuàng)建時間',
          gmt_modified datetime not null comment '記錄最后修改時間',
          is_deleted tinyint default 0 not null comment '邏輯刪除標識'
          ) engine
          = InnoDB default charset=utf8;
          復制代碼

          現(xiàn)在有需求:

          統(tǒng)計 2000 年三門學科 ('英語', '數(shù)學', '語文') 及格分數(shù)按學期, 學科統(tǒng)計最低分,最高分和平均分, 且樣本數(shù)需要大于 1 條, 統(tǒng)計結(jié)果按學期和學科排序

          我們可以寫 SQL 語句如下

          select school_term,
          subject,
          count(score) as count,
          min(score) as min_score,
          max(score) as max_score,
          avg(score) as max_score
          from student_score
          where school_term >= 2000
          and subject in ('英語', '數(shù)學', '語文')
          and score >
          = 60
          and is_deleted = 0
          group by school_term, subject
          having count(score) > 1
          order by school_term, subject
          ;
          復制代碼

          那上面的需求,分別用 fluent mybatis, 原生 mybatis 和 Mybatis plus 來實現(xiàn)一番。

          使用 fluent mybatis 來實現(xiàn)上面的功能

          具體代碼

          我們可以看到 fluent api 的能力,以及 IDE 對代碼的渲染效果。

          換成 mybatis 原生實現(xiàn)效果

          1. 定義 Mapper 接口

          public interface MyStudentScoreMapper {
          List<Map<String, Object>> summaryScore(SummaryQuery paras);
          }
          復制代碼

          1. 定義接口需要用到的參數(shù)實體 SummaryQuery

          @Data
          @Accessors(chain = true)
          public class SummaryQuery {
          private Integer schoolTerm;

          private List<String> subjects;

          private Integer score;

          private Integer minCount;
          }
          復制代碼

          1. 定義實現(xiàn)業(yè)務(wù)邏輯的 mapper xml 文件

          <select resultType="map" parameterType="cn.org.fluent.mybatis.springboot.demo.mapper.SummaryQuery">
          select school_term,
          subject,
          count(score) as count,
          min(score) as min_score,
          max(score) as max_score,
          avg(score) as max_score
          from student_score
          where school_term >= #{schoolTerm}
          and subject in
          <foreach collection="subjects" item="item" open="(" close=")" separator=",">
          #{item}
          </foreach>
          and score >= #{score}
          and is_deleted = 0
          group by school_term, subject
          having count(score) > #
          {minCount}
          order by school_term, subject
          </select>
          復制代碼

          1. 實現(xiàn)業(yè)務(wù)接口 (這里是測試類, 實際應(yīng)用中應(yīng)該對應(yīng) Dao 類)

          @RunWith(SpringRunner.class)
          @SpringBootTest(classes = QuickStartApplication.class)
          public class MybatisDemo {
          @Autowired
          private MyStudentScoreMapper mapper;

          @Test
          public void mybatis_demo() {

          SummaryQuery paras = new SummaryQuery()
          .setSchoolTerm(2000)
          .setSubjects(Arrays.asList("英語", "數(shù)學", "語文"))
          .setScore(60)
          .setMinCount(1);

          List<Map<String, Object>> summary = mapper.summaryScore(paras);
          System.out.println(summary);
          }
          }
          復制代碼

          總之,直接使用 mybatis,實現(xiàn)步驟還是相當?shù)姆爆崳侍?。那換成 mybatis plus 的效果怎樣呢?

          換成 mybatis plus 實現(xiàn)效果

          mybatis plus 的實現(xiàn)比 mybatis 會簡單比較多,實現(xiàn)效果如下

          如紅框圈出的,寫 mybatis plus 實現(xiàn)用到了比較多字符串的硬編碼(可以用 Entity 的 get lambda 方法部分代替字符串編碼)。字符串的硬編碼,會給開發(fā)同學造成不小的使用門檻,個人覺的主要有 2 點:

          1. 字段名稱的記憶和敲碼困難

          2. Entity 屬性跟隨數(shù)據(jù)庫字段發(fā)生變更后的運行時錯誤

          其他框架,比如 TkMybatis 在封裝和易用性上比 mybatis plus 要弱,就不再比較了。

          fluent mybatis 生成代碼設(shè)置

          public class AppEntityGenerator {
          static final String url = "jdbc:mysql://localhost:3306/fluent_mybatis_demo?useSSL=false&useUnicode=true&characterEncoding=utf-8";

          public static void main(String[] args) {
          FileGenerator.build(Abc.class);
          }

          @Tables(
          /** 數(shù)據(jù)庫連接信息 **/
          url = url, username = "root", password = "password",
          /** Entity類parent package路徑 **/
          basePack = "cn.org.fluent.mybatis.springboot.demo",
          /** Entity代碼源目錄 **/
          srcDir = "spring-boot-demo/src/main/java",
          /** Dao代碼源目錄 **/
          daoDir = "spring-boot-demo/src/main/java",
          /** 如果表定義記錄創(chuàng)建,記錄修改,邏輯刪除字段 **/
          gmtCreated = "gmt_create", gmtModified = "gmt_modified", logicDeleted = "is_deleted",
          /** 需要生成文件的表 ( 表名稱:對應(yīng)的Entity名稱 ) **/
          tables = @Table(value = {"student_score"})
          )

          static class Abc {
          }
          }
          復制代碼

          mybatis plus 代碼生成設(shè)置

          public class CodeGenerator {

          static String dbUrl = "jdbc:mysql://localhost:3306/fluent_mybatis_demo?useSSL=false&useUnicode=true&characterEncoding=utf-8";

          @Test
          public void generateCode() {
          GlobalConfig config = new GlobalConfig();
          DataSourceConfig dataSourceConfig = new DataSourceConfig();
          dataSourceConfig.setDbType(DbType.MYSQL)
          .setUrl(dbUrl)
          .setUsername("root")
          .setPassword("password")
          .setDriverName(Driver.class.getName());
          StrategyConfig strategyConfig = new StrategyConfig();
          strategyConfig
          .setCapitalMode(true)
          .setEntityLombokModel(false)
          .setNaming(NamingStrategy.underline_to_camel)
          .setColumnNaming(NamingStrategy.underline_to_camel)
          .setEntityTableFieldAnnotationEnable(true)
          .setFieldPrefix(new String[]{"test_"})
          .setInclude(new String[]{"student_score"})
          .setLogicDeleteFieldName("is_deleted")
          .setTableFillList(Arrays.asList(
          new TableFill("gmt_create", FieldFill.INSERT),
          new TableFill("gmt_modified", FieldFill.INSERT_UPDATE)));

          config
          .setActiveRecord(false)
          .setIdType(IdType.AUTO)
          .setOutputDir(System.getProperty("user.dir") + "/src/main/java/")
          .setFileOverride(true);

          new AutoGenerator().setGlobalConfig(config)
          .setDataSource(dataSourceConfig)
          .setStrategy(strategyConfig)
          .setPackageInfo(
          new PackageConfig()
          .setParent("com.mp.demo")
          .setController("controller")
          .setEntity("entity")
          ).execute();
          }
          }
          復制代碼

          看完 3 個框架對同一個功能點的實現(xiàn), 各位看官肯定會有自己的判斷,筆者這里也總結(jié)了一份比較。


          —————END—————

          推薦閱讀:

          推薦7個牛哄哄 Spring Cloud 實戰(zhàn)項目
          基于 SpringBoot + Vue 框架開發(fā)的網(wǎng)頁版聊天室項目
          基于 SpringBoot + Vue 實現(xiàn)的可視化拖拽編輯的大屏項目
          Github上10個超好看 可視化面板,后臺管理頁面有著落了
          這可能是史上功能最全的Java權(quán)限認證框架!

          最近面試BAT,整理一份面試資料Java面試BAT通關(guān)手冊,覆蓋了Java核心技術(shù)、JVM、Java并發(fā)、SSM、微服務(wù)、數(shù)據(jù)庫、數(shù)據(jù)結(jié)構(gòu)等等。
          獲取方式:關(guān)注公眾號并回復 java 領(lǐng)取,更多內(nèi)容陸續(xù)奉上。
          明天見(??ω??)??
          瀏覽 108
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  久久日网站| 久久婷婷六月 | 久久精品成人电影 | 亚洲免费在线视频观看 | 四虎av|