MybatisPlusPro讓CURD開發(fā)效率直接拉滿
一、MybatisPlusPro 是什么鬼?
先給大家講個扎心的故事:我司有個叫富貴的同學(xué),天天用 MybatisPlus 寫 DAO 層,覺得這玩意兒確實(shí)香,CRUD 操作分分鐘搞定。但問題來了,上到 Controller 層,他發(fā)現(xiàn)每個接口都得重復(fù)寫 Service 和 Mapper 的調(diào)用,代碼像 “套娃” 一樣,搬磚搬得手都酸了。
于是,富貴同學(xué)一氣之下,擼了個MybatisPlusPro—— 說白了,就是在 MybatisPlus 的基礎(chǔ)上再封裝一層,把通用的 CURD 功能從 Service 擴(kuò)展到 Controller。只要你的 Controller 繼承BaseController,所有的增刪改查接口自動擁有,連分頁、排序、統(tǒng)計都給你配得明明白白!
舉個栗子:
@RestController
@RequestMapping("/blog")
public class BlogController extends BaseController<Blog, BlogService> {
? ? // 啥也不用寫,直接繼承BaseController
}就這么簡單,前端直接調(diào)接口,媽媽再也不用擔(dān)心我的 CRUD!
二、核心功能解析:懶人福音
1. 一行代碼搞定 CRUD
BaseController 提供了標(biāo)準(zhǔn)的 REST 風(fēng)格接口,增刪改查全搞定:
- 增:/insert 接口,直接傳實(shí)體對象就能插入數(shù)據(jù)庫。
- 刪:/deleteById 接口,支持批量刪除,傳個 ID 列表就行。
- 改:/updateById 接口,自動根據(jù) ID 更新數(shù)據(jù)。
- 查:/getById 接口,根據(jù) ID 查詢單條數(shù)據(jù)。
- 存:/save 接口,自動判斷是插入還是更新。
這一套組合拳下來,以前寫一個接口的時間,現(xiàn)在能寫十個!
2. 分頁查詢:前端直接 “抄作業(yè)”
分頁查詢是后端開發(fā)的 “家常便飯”,MybatisPlusPro 直接幫你封裝好了:
@PostMapping("/page")
public ResponseUtils page(@RequestBody PageParamDto<Blog> pageParamDto) {
? ? // 自動處理分頁參數(shù),限制每頁最大100條
? ? Page<Blog> page = new Page<>(pageParamDto.getPage(), pageParamDto.getSize());
? ? QueryWrapper<Blog> queryWrapper = new QueryWrapper<>();
? ? // 處理升序、降序參數(shù)
? ? if (!StrUtil.isEmpty(pageParamDto.getAsc())) {
? ? ? ? queryWrapper.orderByAsc(pageParamDto.getAsc().split(","));
? ? }
? ? if (!StrUtil.isEmpty(pageParamDto.getDesc())) {
? ? ? ? queryWrapper.orderByDesc(pageParamDto.getDesc().split(","));
? ? }
? ? return ResponseUtils.success(baseService.page(page, queryWrapper));
}前端只需要傳個 JSON 參數(shù):
{
? "page": 1,
? "size": 10,
? "asc": "create_time",
? "desc": "id"
}就能拿到分頁數(shù)據(jù),連排序都不用自己寫 SQL!
3. 動態(tài)查詢:反射幫你 “偷懶”
MybatisPlusPro 還支持動態(tài)查詢,通過反射自動構(gòu)建查詢條件:
@PostMapping("/list")
public ResponseUtils list(@RequestBody Blog blog) {
? ? QueryWrapper<Blog> queryWrapper = ApprenticeUtil.getQueryWrapper(blog);
? ? return ResponseUtils.success(baseService.list(queryWrapper));
}比如前端傳個{"title": "MybatisPlusPro"},就會自動生成WHERE title = 'MybatisPlusPro'的條件,是不是很神奇?
三、高級特性:讓 CRUD 更優(yōu)雅
1. 數(shù)據(jù)審計:對賬不再頭大
Mybatis-Mate 模塊提供了數(shù)據(jù)審計功能,比如銀行流水對賬,自動對比兩個對象的屬性差異:
// 異步回調(diào)方式
applicationEventPublisher.publishEvent(new DataAuditEvent((t) -> {
? ? List<Change> changes = t.apply(newVersion, oldVersion);
? ? changes.forEach(change -> {
? ? ? ? ValueChange valueChange = (ValueChange) change;
? ? ? ? System.err.println(String.format("%s不匹配,期望值 %s 實(shí)際值 %s",
? ? ? ? ? ? ? ? valueChange.getPropertyName(), valueChange.getLeft(), valueChange.getRight()));
? ? });
}));
// 手動調(diào)用方式
DataAuditor.compare(obj1, obj2);有了這個功能,再也不用擔(dān)心數(shù)據(jù)不一致的問題了!
2. 數(shù)據(jù)權(quán)限:精準(zhǔn)控制訪問
通過@DataScope注解,可以實(shí)現(xiàn)行級粒度的權(quán)限控制,比如上級部門只能查看子部門的數(shù)據(jù):
@DataScope(type = "test", value = {
? ? @DataColumn(alias = "u", name = "department_id"),
? ? @DataColumn(alias = "u", name = "mobile")
})
@Select("select u.* from user u")
List<User> selectTestList(IPage<User> page, Long id, @Param("name") String username);最終生成的 SQL 會自動添加權(quán)限條件:
SELECT u.* FROM user u WHERE (u.department_id IN ('1', '2', '3', '5')) AND u.mobile LIKE '%1533%'3. 表結(jié)構(gòu)自動維護(hù):告別手動改表
Mybatis-Mate 還支持?jǐn)?shù)據(jù)庫表結(jié)構(gòu)的自動維護(hù),比如新增字段、修改字段類型:
@Component
public class MysqlDdl implements IDdl {
? ? @Override
? ? public List<String> getSqlFiles() {
? ? ? ? return Arrays.asList("db/tag-schema.sql", "D:\\db\\tag-data.sql");
? ? }
}首次執(zhí)行會在數(shù)據(jù)庫中生成ddl_history表,記錄每次執(zhí)行的 SQL 腳本,以后升級表結(jié)構(gòu)就像 “傻瓜式安裝” 一樣簡單!
四、性能優(yōu)化:讓 CRUD 飛起來
1. 批量插入:效率提升 2000%
傳統(tǒng)的逐條插入簡直是 “龜速”,MybatisPlusPro 提供了批量插入優(yōu)化方案:
開啟 rewriteBatchedStatements 參數(shù):
jdbc:mysql://localhost:3306/db_name?rewriteBatchedStatements=true
預(yù)先生成 ID:
long examId = zzidc.nextId(); // 雪花算法生成全局唯一ID exam.setId(examId); examMapper.insert(exam);
使用 saveBatch 方法:
List<Question> questionList =?new?ArrayList<>();
for?(int?i =?0; i <?10000; i++) {
? ? Question question =?new?Question();
? ? question.setId(zzidc.nextId());
? ? questionList.add(question);
}
questionService.saveBatch(questionList,?1000);?// 分批插入,每批1000條實(shí)測數(shù)據(jù):傳統(tǒng)逐條插入 1 萬條數(shù)據(jù)需要 12 秒,而優(yōu)化后僅需 0.5 秒,性能提升2000%!
2. 分頁優(yōu)化:避免全表掃描
優(yōu)化 Count 查詢:
// 用count(1)代替count(*)
queryWrapper.select("count(1) as total");避免排序字段無索引:
// 確保排序字段有索引
@TableIndex("idx_create_time")
private?Date?create_time;3. 樂觀鎖:高并發(fā)下的數(shù)據(jù)安全
在高并發(fā)場景下,樂觀鎖可以防止數(shù)據(jù)覆蓋:
// 實(shí)體類添加@Version注解
@Version
private?Integer version;
// 配置樂觀鎖插件
@Bean
public?MybatisPlusInterceptor?mybatisPlusInterceptor()?{
? ? MybatisPlusInterceptor interceptor =?new?MybatisPlusInterceptor();
? ? interceptor.addInnerInterceptor(new?OptimisticLockerInnerInterceptor());
? ??return?interceptor;
}當(dāng)多個線程同時更新數(shù)據(jù)時,只有版本號一致的線程才能成功,避免了臟讀和幻讀。
五、實(shí)戰(zhàn)案例:考試系統(tǒng)中的批量插入
以考試系統(tǒng)為例,創(chuàng)建一份試卷需要插入試卷、題目、選項等多張表的數(shù)據(jù)。使用 MybatisPlusPro 的批量插入功能,輕松搞定:
@Service
publicclass?ExamServiceImpl?implements?ExamService?{
? ??@Autowired
? ??private?ExamMapper examMapper;
? ??@Autowired
? ??private?QuestionService questionService;
? ??@Autowired
? ??private?OptionService optionService;
? ??privatestaticfinalint?BATCH_SIZE =?2000;
? ??@Override
? ??@Transactional(rollbackFor = Exception.class)
? ??public?void?createExam(Exam exam,?int?questionCount,?int?optionCountPerQuestion)?{
? ? ? ??// 預(yù)先生成試卷ID
? ? ? ??long?examId = zzidc.nextId();
? ? ? ? exam.setId(examId);
? ? ? ? examMapper.insert(exam);
? ? ? ? List<Question> questionList =?new?ArrayList<>();
? ? ? ? List<Option> allOptionList =?new?ArrayList<>();
? ? ? ??for?(int?i =?0; i < questionCount; i++) {
? ? ? ? ? ??// 預(yù)先生成題目ID
? ? ? ? ? ??long?questionId = zzidc.nextId();
? ? ? ? ? ? Question question =?new?Question();
? ? ? ? ? ? question.setId(questionId);
? ? ? ? ? ? question.setExamId(examId);
? ? ? ? ? ? questionList.add(question);
? ? ? ? ? ??// 生成選項數(shù)據(jù)
? ? ? ? ? ??for?(int?j =?0; j < optionCountPerQuestion; j++) {
? ? ? ? ? ? ? ? Option option =?new?Option();
? ? ? ? ? ? ? ? option.setId(zzidc.nextId());
? ? ? ? ? ? ? ? option.setQuestionId(questionId);
? ? ? ? ? ? ? ? allOptionList.add(option);
? ? ? ? ? ? }
? ? ? ? }
? ? ? ??// 批量插入題目和選項
? ? ? ? questionService.saveBatch(questionList, BATCH_SIZE);
? ? ? ? optionService.saveBatch(allOptionList, BATCH_SIZE);
? ? }
}整個過程行云流水,再也不用為批量插入的性能問題發(fā)愁了!
六、版本更新:2025 最新特性
MybatisPlusPro 在 2025 年 4 月發(fā)布的 3.5.12 版本中,新增了不少實(shí)用功能:
- 雪花 ID 配置:支持手動分配 workerId 和 datacenterId,或者指定網(wǎng)卡信息自動獲取,徹底解決分布式 ID 生成問題。
- 批量操作增強(qiáng):BaseMapper 新增批量操作方法,返回值支持 List,方便處理批量操作結(jié)果。
- 邏輯刪除優(yōu)化:Service 層邏輯刪除默認(rèn)支持填充,避免手動處理刪除標(biāo)記。
- SQL 注入防護(hù):UpdateWrapper 增加 checkSqlInjection 方法,防止惡意 SQL 注入。
七、總結(jié):MybatisPlusPro vs MybatisPlus
| 功能 | MybatisPlus | MybatisPlusPro |
|---|---|---|
| Controller 層 | 需要手動編寫 CRUD 接口 | 繼承 BaseController 自動生成接口 |
| 分頁排序 | 需要手動處理 Page 和 Wrapper | 自動處理分頁參數(shù),支持動態(tài)排序 |
| 批量操作 | 提供 saveBatch 方法 | 結(jié)合 rewriteBatchedStatements 優(yōu)化 |
| 數(shù)據(jù)權(quán)限 | 需自定義攔截器 | 內(nèi)置 @DataScope 注解,一鍵實(shí)現(xiàn) |
| 表結(jié)構(gòu)維護(hù) | 需手動執(zhí)行 SQL 腳本 | 自動維護(hù)表結(jié)構(gòu),支持多數(shù)據(jù)源 |
從表格可以看出,MybatisPlusPro 在開發(fā)效率和功能完整性上都更勝一籌,堪稱 CURD 開發(fā)的 “瑞士軍刀”!
八、寫在最后
MybatisPlusPro 的出現(xiàn),徹底改變了我對 CURD 開發(fā)的認(rèn)知。它不僅讓代碼量大幅減少,還通過各種高級特性和性能優(yōu)化,讓開發(fā)變得更加優(yōu)雅和高效。如果你還在為 Controller 層的 CRUD 接口而煩惱,不妨試試 MybatisPlusPro,相信你會和我一樣,愛上這種 “懶人式” 開發(fā)!
到此這篇關(guān)于MybatisPlusPro讓CURD開發(fā)效率直接拉滿的文章就介紹到這了,更多相關(guān)MybatisPlusPro CURD開發(fā)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
MybatisPlus 不修改全局策略和字段注解如何將字段更新為null
這篇文章主要介紹了MybatisPlus 不修改全局策略和字段注解如何將字段更新為null,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2021-04-04
java使用HashMap實(shí)現(xiàn)斗地主(有序版)
這篇文章主要為大家詳細(xì)介紹了java使用ArrayList實(shí)現(xiàn)斗地主游戲,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下2021-03-03
詳解SpringBoot中的參數(shù)校驗(yàn)(項目實(shí)戰(zhàn))
這篇文章主要介紹了SpringBoot中的參數(shù)校驗(yàn),本文通過實(shí)例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2020-07-07
Java數(shù)據(jù)結(jié)構(gòu)之加權(quán)無向圖的設(shè)計實(shí)現(xiàn)
加權(quán)無向圖是一種為每條邊關(guān)聯(lián)一個權(quán)重值或是成本的圖模型。這種圖能夠自然地表示許多應(yīng)用。這篇文章主要介紹了加權(quán)無向圖的設(shè)計與實(shí)現(xiàn),感興趣的可以了解一下2022-11-11
SpringBoot 如何根據(jù)不同profile選擇不同配置
這篇文章主要介紹了SpringBoot 如何根據(jù)不同profile選擇不同配置的操作方式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教2021-08-08

