1. 前言
在上一文中我根據Mybatis中Mapper的生命周期手動實現了一個簡單的通用Mapper功能,但是遺憾的是它缺乏實際生產的檢驗。因此我選擇更加成熟的一個Mybatis開發增強包。它就是已經獲得Gitee獲得 6900 star 的Mybatis Plus。
Gitee: https://gitee.com/felord/kono day04 分支
GitHub: https://github.com/NotFound403/kono day04 分支
2. Mybatis Plus的優勢
我認為如果你需要在你的框架中引用第三方包,需要考量的最大因素不是它功能的強大而是它社區的活躍度。文檔是否齊全,是否擁有完善的Q/A,版本維護周期是否持續。目前來看Mybatis Plus經過數年的打磨算是比較成熟的類庫。目前我認為它幾個突出的優點:
- 單表的通用Mapper功能,這個算一個基本的需求。
- 在單表查詢的基礎之上增加了語義化查詢,可通過
UpdateWrapper
、QueryWrapper
等條件構造器豐富單表個性化操作。 - 多種主鍵策略的支持,常見的UUID、雪花算法等。
- 基礎的代碼生成器,減少樣板代碼編寫、提高效率的利器。
- 其它還有一些多租戶、樂觀鎖等功能。
3. 集成依賴
以mybatis-plus-boot-starter 3.3.2 版本為例。
我們只需要將kono項目day02分支pom.xml
中的mybatis-spring-boot-starter
依賴替換為即可:
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
</dependency>
如果你還需要代碼生成器功能請引入下面的模塊:
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<scope>compile</scope>
<optional>true</optional>
</dependency>
<!-- 引入freemarker包作為代碼生成器引擎-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-freemarker</artifactId>
<scope>compile</scope>
<optional>true</optional>
</dependency>
關於代碼生成器可參閱Mybatis Plus代碼生成器和Java代碼生成器的原理這兩篇文章,本文不再對代碼生成器進行詳細解釋。
4. 配置
Mybatis Plus重寫了starter,所以配置上有了變化。使用原生Mybatis的Starter配置為:
mybatis:
configuration:
# 下划線轉駝峰
map-underscore-to-camel-case: true
# 掃描 xml 文件位置
mapper-locations: classpath:mapper/*Mapper.xml
對應的Mybatis Plus配置為:
mybatis-plus:
configuration:
# 下划線轉駝峰
map-underscore-to-camel-case: true
# 掃描 xml 文件位置
mapper-locations: classpath:mapper/*Mapper.xml
我們還可以增加一些Mybatis Plus所集成的特性,諸如新增修改查詢填充策略、邏輯刪除、主鍵填充等等個性化能力。這里以最常用的主鍵填充策略為例,如果我們使用分布式主鍵策略雪花算法的話,可以增加如下配置:
mybatis-plus:
global-config:
db-config:
id-type: assign_id
分頁也是我們非常常用的功能,最后我們加入Mybatis Plus分頁功能,整體的配置如下:
/**
* mybatis configuration.
*
* @author felord.cn
*/
@MapperScan("cn.felord.kono.mapper")
@Configuration
public class MybatisConfiguration {
/**
* 分頁插件
*/
@Bean
public PaginationInterceptor paginationInterceptor() {
return new PaginationInterceptor();
}
}
請注意這里的分頁只支持一對一分頁,一對多分頁還不支持。原因請閱讀一對多分頁SQL應該怎么寫。
5. 使用
Mybatis Plus使用了一種叫Active Record的領域模型范式,特點是一個模型類(Model)對應關系型數據庫中的一個表(table),而模型類的一個實例對應表中的一行記錄。因此我們的POJO對象這么編寫,以UserInfo
為例:
/**
* @author felord.cn
* @since 15:43
**/
@EqualsAndHashCode(callSuper = false)
@Data
public class UserInfo extends Model<UserInfo> {
private static final long serialVersionUID = -8938650956516110149L;
@TableId
private Long userId;
private String name;
private Integer age;
@Override
protected Serializable pkVal() {
return this.userId;
}
}
不適用lombok的情況下請對POJO增加Getter/Setter方法。
對應的Mapper接口只需要繼承BaseMapper
就可以了:
public interface UserInfoMapper extends BaseMapper<UserInfo> {}
這時就已經具有了通用Mapper提供的一些接口能力了,當然你可以使用傳統的模式去實現自定義的操作方法。
服務層的接口范式是這樣的,需要繼承IService
接口:
public interface UserInfoService extends IService<UserInfo> {}
實現類UserInfoServiceImpl
同時繼承了ServiceImpl
:
@Service
public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo> implements UserInfoService {
}
接下來就是使用了,首先我們來用通用Mapper進行查詢:
final String userId ="12334343455457";
UserInfo byId = userInfoService.getById(userId);
我們也可以使用更加靈活的方式來實現上面的查詢:
final String userId ="12334343455457";
UserInfo one = userInfoService.getOne(new QueryWrapper<UserInfo>().lambda()
.eq(UserInfo::getUserId, userId));
你可以根據你的業務靈活地增加更多的條件或者指定查詢字段進行單表查詢,而無需編寫SQL,其它新增、更新、刪除同理。對於上面的范式,Mybatis Plus提供了代碼生成器來實現,詳情請參閱我在Mybatis Plus代碼生成器一文中的講解。
6. 總結
到這里基本的Mybatis Plus整合就完成了,更多特性可去官方文檔去了解使用。多多關注:碼農小胖哥 繼續來和我一起整合腳手架。
關注公眾號:Felordcn 獲取更多資訊