Mybatis Plus之內置Mapper實踐


MyBatis Plus,作為對MyBatis的進一步增強,大大簡化了我們的開發流程,提高了開發速度

配置

由於Mybatis Plus是建立在Mybatis之上的,所以其已經依賴了Mybatis,故我們無需在項目中顯式地重復添加Mybatis依賴。直接在POM文件中Mybatis Plus依賴即可

<!--Mybatis Plus--> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-boot-starter</artifactId> <version>3.4.1</version> </dependency> 

Mapper CRUD操作

在Mybatis下,需要我們自行編寫Mapper接口文件、提供sql的的xml文件。眾所周知,這些CRUD的接口寫起來不僅繁瑣還容易出錯,為此在Mybatis Plus中提供了內置的Mapper。高效實現CRUD操作

-- 創建數據表 create table t_people_info ( id int not null auto_increment comment 'ID', name varchar(255) null comment '姓名', sex varchar(255) null comment '性別', primary key (id) ) comment '信息表'; 

POJO類定義如下,這里展示了@TableName、@TableField注解的用法

import com.baomidou.mybatisplus.annotation.TableField; import com.baomidou.mybatisplus.annotation.TableId; import com.baomidou.mybatisplus.annotation.TableName; @Data @Builder @AllArgsConstructor @NoArgsConstructor @TableName("t_people_info") // 指定數據庫的表名 public class People { /**  * ID  */ private int id; /**  * 姓名  */ @TableField("name") // 該屬性在數據表中對應的字段名  private String username; /**  * 性別  */ private String sex; /**  * 職業  */ @TableField(exist = false) // 該屬性在數據表中不存在  private String job; } 

而Mapper接口文件只需繼承BaseMapper即可獲得Mybatis Plus提供的基本的CRUD功能,無需我們定義接口及相關的SQL。當然如果需要復雜的操作直接在PeopleMapper接口中繼續添加即可

import com.baomidou.mybatisplus.core.mapper.BaseMapper; public interface PeopleMapper extends BaseMapper<People> { } 

public class ProperService { @Autowired private PeopleMapper peopleMapper; public void testInsert() { List<People> list = new LinkedList<>(); list.add( People.builder().username("小明").build() ); list.add( People.builder().id(10).username("老王").sex("男").build() ); list.add( People.builder().id(11).username("老張").sex("女").build() ); list.add( People.builder().id(12).sex("女").build() ); for (People people : list) { peopleMapper.insert(people); } } } 

根據ID刪除及批量操作,方式如下

/**  * 根據ID刪除  */ public void testDeleteById() { peopleMapper.deleteById(10); } /**  * 根據ID批量刪除  */ public void testDeleteByIds() { List ids = new LinkedList(); ids.add(11); ids.add(12); peopleMapper.deleteBatchIds( ids ); } 

與此同時,也支持基於條件的刪除

/**  * 根據條件刪除  */ public void testDeleteByParam1() { // 表字段map  Map map = new HashMap(); // Note:這里設置條件應使用數據表的字段名,而不是Java類的屬性名  map.put("name", "匿名用戶"); map.put("sex", "男"); // 多個條件為and的關系  int num = peopleMapper.deleteByMap(map); System.out.println("delete num : " + num); } /**  * 根據條件刪除  */ public void testDeleteByParam2() { // Note:此時其實隱含了 id為null 的條件  People people = People.builder() .username("翠花") .sex("女") .build(); // 多個條件為and的關系  QueryWrapper<People> wrapper = new QueryWrapper<>(people); int num = peopleMapper.delete( wrapper ); System.out.println("delete num : " + num); } 

同理對於更新操作,支持基於ID的操作方式

/**  * 根據ID更新  */ public void testUpdateById() { People people = People.builder() .id(3) .username("孫尚香") .build(); peopleMapper.updateById(people); } 

上述更新語句執行后會發現,id為3的記錄,對於name字段確實被更新為 "孫尚香" 了,但是如果sex字段並不會被更新為 NULL。這是因為@TableField注解的updateStrategy屬性默認為NOT_NULL所導致的。該屬性常用的值及釋義如下所示

  • NOT_NULL:要求新值非NULL
  • NOT_EMPTY:要求新值非NULL、非空字符串
  • IGNORED:新值可以為NULL、空字符串

故我們在sex屬性上使用@TableField注解,並把updateStrategy設置為FieldStrategy.IGNORED后,上述測試代碼對sex字段的更新才會生效

/**  * 性別  */ @TableField(updateStrategy = FieldStrategy.IGNORED) private String sex; 

與此同時,也支持基於條件的更新。而且可以看到在基於ID的更新方式中,需要修改@TableField注解的updateStrategy屬性,來保證可以更新為NULL、空字符串。顯然非常麻煩,而且容易出錯。而通過updateWrapper的set方法來設置新值,顯式地設置NULL值就非常直觀了,不容易出錯

/**  * 根據條件更新  */ public void testUpdateByParam() { UpdateWrapper<People> updateWrapper = new UpdateWrapper<>(); // Note:這里應使用數據表的字段名,而不是Java類的屬性名  // where 條件:id 大於 50  updateWrapper.gt("id",50); // set 新值:sex 更新為 男  updateWrapper.set("sex","男"); // set 新值:name 更新為 NULL  updateWrapper.set("name","null"); // 多個條件為and的關系  peopleMapper.update(null, updateWrapper); } 

根據ID查詢及批量操作,方式如下

/**  * 根據ID查詢  */ public void testSelectById() { People people = peopleMapper.selectById(1); System.out.println("people: " + people); } /**  * 根據ID批量查詢  */ public void testSelectByIds() { List list = new LinkedList(); list.add(1); list.add(2); list.add(3); List<People> peopleList = peopleMapper.selectBatchIds(list); peopleList.forEach(System.out::println); } 

與此同時,也支持基於條件的查詢。其中查詢條件為空,則查詢全部

/**  * 根據條件查詢。其中查詢條件為空,則查詢全部  */ public void testSelectAll() { List<People> list = peopleMapper.selectList(null); list.forEach( System.out::println ); } /**  * 根據條件查詢  */ public void testSelectByParam1() { QueryWrapper<People> queryWrapper = new QueryWrapper<>(); // Note:這里設置條件應使用數據表的字段名,而不是Java類的屬性名  // 條件:性別為男  queryWrapper.eq("sex", "男"); // 條件:id 小於等於 100  queryWrapper.le("id", 50); // 多個條件為and的關系  List<People> list = peopleMapper.selectList(queryWrapper); list.forEach(System.out::println); } /**  * 根據條件查詢  */ public void testSelectByParam2() { // 表字段map  Map<String, Object> map = new HashMap<>(); map.put("sex", "女"); // Note:這里設置條件應使用數據表的字段名,而不是Java類的屬性名  map.put("name", "佳麗"); // 多個條件為and的關系  List<People> list = peopleMapper.selectByMap(map); list.forEach(System.out::println); } 

有時候我們還需要進行分頁查詢,在Mybatis Plus下也是非常方便的,只需配置下分頁插件即可

@Configuration public class MybatisPlusConfig { /**  * Mybatis Plus 分頁插件  * @return  */ @Bean public MybatisPlusInterceptor innerInterceptor() { MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor(); interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL)); return interceptor; } } 

關於分頁查詢的操作方式如下所示:

/**  * 分頁查詢  */ public void testSelectByPage() { // 查詢條件  QueryWrapper<People> queryWrapper = new QueryWrapper<>(); // Note:這里設置條件應使用數據表的字段名,而不是Java類的屬性名  // 條件:id 大於 2  queryWrapper.gt("id", 2); // 條件:name字段 (右)模糊匹配 "張%"  queryWrapper.likeRight("name", "張"); // 分頁參數: 頁碼:2, 單頁大小:10  Page<People> page = new Page<>(2,10); // 分頁查詢, 多個條件為and的關系  Page<People> result = peopleMapper.selectPage(page2, queryWrapper); System.out.println("people List: " + result.getRecords() ); } 

邏輯刪除

對於內置Mapper,Mybatis Plus可以自動支持邏輯刪除的功能。通過@TableLogic注解指定邏輯刪除字段即可

/**  * 邏輯刪除標識,invalid:無效;valid:有效  */ @TableLogic private String flag; 

而對於邏輯未刪除的值、已刪除的值即可直接通過注解配置,亦可進行全局配置

# Mybatis Plus 全局設置,邏輯已刪除值
mybatis-plus.global-config.db-config.logic-delete-value=invalid
# Mybatis Plus 全局設置,邏輯未刪除值
mybatis-plus.global-config.db-config.logic-not-delete-value=valid

為了實現邏輯刪除,內置Mapper在自動注入SQL時也會發生一些變化。具體地:

  • 插入:無變化
  • 查找:一方面會追加where條件以過濾掉已刪除的記錄,另一方面,通過wrapper指定條件也會忽略邏輯刪除字段的條件
  • 更新:一方面會追加where條件防止對已刪除的記錄進行更新,另一方面,通過wrapper指定條件也會忽略邏輯刪除字段的條件
  • 刪除:轉變為更新語句,將 邏輯刪除字段 設置為 邏輯已刪除值

Note

對於主鍵,Mybatis Plus還支持在未指定主鍵的時候自動生成ID或UUID。具體地,其支持對某個表的單獨設置、全局設置。前者可通過在主鍵屬性上設置@TableId注解的type屬性為IdType.ASSIGN_ID、IdType.ASSIGN_UUID實現;后者則可通過在配置文件中設置配置項 mybatis-plus.global-config.db-config.id-type 為 assign_id、assign_uuid 實現


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM