最近逛開源社區的時候,偶爾發現了一個 MyBatis 增強框架-MyBatis-Flex ,感覺挺不錯的,集合了 MyBatis-Plus、Fluent-MyBatis 的優點。
MyBatis-Flex 的作者是一位技術大佬,還開源了知名 CMS 系統 JPress 以及微服務框架 JFinal。
個人認為這個框架還是挺有潛力的,準備后面在個人項目中試試。同時,也希望這個項目能夠持續維護下去,不斷完善。
MyBatis-Flex 介紹
根據官網介紹,MyBatis-Flex 是一個優雅的 MyBatis 增強框架,具備下面這些特點:
- 輕量:除了 MyBatis 本身,再無任何第三方依賴。
- 靈活且強大:提供了非常靈活的 QueryWrApper,支持關聯查詢、多表查詢、多主鍵、邏輯刪除、樂觀鎖更新、數據填充、數據脫敏、等等....。
- 性能高:性能比傳統的 MyBatis 增強框架比如 MyBatis-Plus 要更優秀。
MyBatis-Flex 幾乎支持所有主流的數據庫,例如,MySQL、MariaDB、DB2、PostgreSQL、SQLite、達夢、人大金倉等等。并且,還可以通過自定義方言的方式,持續添加更多的數據庫支持。
多提一點:QueryWrapper 是 MyBatis-Flex 的核心類,增刪改、查詢和分頁都是借助 QueryWrapper 實現的。并且,QueryWrapper 可以被序列化通過 RPC 進行傳輸,因此,在微服務項目中,我們可以在客戶端(網關、Controller 層等)構造出 QueryWrapper,傳給 Provider 層進行查詢返回數據。
MyBatis-Flex vs MyBatis-Plus
MyBatis-Flex 直接對標老牌 MyBatis 增強框架 MyBatis-Plus,根據官方文檔顯示,其在功能性和性能上都要更優秀一些。
MyBatis-Flex 和 MyBatis-Plus 的功能對比如下(數據來源于 MyBatis-Flex 官方文檔):
從上圖可以看到,像數據填充、數據脫敏、字段權限等 MyBatis-Plus 收費才能使用的功能,MyBatis-Flex 直接可以免費使用。
MyBatis-Flex 和 MybAIts-Plus 的性能對比,大家可以直接看官方文檔提供的數據即可(地址:https://mybatis-flex.com/zh/intro/benchmark.html)。根據官方提供的案例的測試結果顯示,MyBatis-Flex 的綜合性能表現大概是 MyBatis-Plus 的 5~10 倍左右。
- MyBatis-Flex 的查詢單條數據的速度,大概是 MyBatis-Plus 的 5 ~ 10+ 倍。
- MyBatis-Flex 的查詢 10 條數據的速度,大概是 MyBatis-Plus 的 5~10 倍左右。
- Mybatis-Flex 的分頁查詢速度,大概是 Mybatis-Plus 的 5~10 倍左右。
- Mybatis-Flex 的數據更新速度,大概是 Mybatis-Plus 的 5~10+ 倍。
測試源碼在這里:https://gitee.com/mybatis-flex/mybatis-benchmark ,如果對數據存疑的話,可以自行本地測試一下。
下面再來簡單對比一下 MyBatis-Flex 和 Mybaits-Plus 在寫法上的區別。
1、基礎查詢
MyBatis-Flex:
QueryWrapper query = QueryWrapper.create()
.where(EMPLOYEE.LAST_NAME.like(searchword)) //條件為null時自動忽略
.and(EMPLOYEE.GENDER.eq(1))
.and(EMPLOYEE.AGE.gt(24));
List<Employee> employees = employeeMapper.selectListByQuery(query);
MyBatis-Plus:
QueryWrapper<Employee> queryWrapper = Wrappers.query()
.like(searchWord != null, "last_name", searchWord)
.eq("gender", 1)
.gt("age", 24);
List<Employee> employees = employeeMapper.selectList(queryWrapper);
或者 MyBatis-Plus 的 lambda 寫法:
LambdaQueryWrapper<Employee> queryWrapper = Wrappers.<Employee>lambdaQuery()
.like(StringUtils.isNotEmpty(searchWord), Employee::getUserName,"B")
.eq(Employee::getGender, 1)
.gt(Employee::getAge, 24);
List<Employee> employees = employeeMapper.selectList(queryWrapper);
2、多表查詢
MyBatis-Flex:
QueryWrapper query = QueryWrapper.create()
.select().from(ACCOUNT)
.leftJoin(ARTICLE).on(ACCOUNT.ID.eq(ARTICLE.ACCOUNT_ID))
.where(ACCOUNT.AGE.ge(10));
List<Account> accounts = mapper.selectListByQuery(query);
MyBatis-Plus:
// 不支持~~~~
3、部分字段更新
MyBatis-Flex :
Account account = UpdateEntity.of(Account.class);
account.setId(100); //設置主鍵
account.setUserName("michael");
account.setAge(18);
account.setBirthday(null);
accountMapper.update(account);
MyBatis-Plus:
UpdateWrapper<Account> updateWrapper = new UpdateWrapper<>();
updateWrapper.eq("id", 100);
updateWrapper.set("user_name", "michael");
updateWrapper.set("age", 18);
updateWrapper.set("birthday", null);
accountMapper.update(null, updateWrapper);
MyBatis-Flex 的核心功能
MyBatis-Flex 的核心功能非常多,這里挑選個別比較有意思的進行簡單介紹,官方文檔已經介紹的非常詳細了。
數據脫敏
數據脫敏說的就是我們根據特定的規則對敏感信息數據進行變形,比如我們把手機號、身份證號某些位數使用 * 來代替。
MyBatis-Flex 提供了 @ColumnMask() 注解,以及內置的 9 種脫敏規則,開箱即用:
- 用戶名脫敏
- 手機號脫敏
- 固定電話脫敏
- 身份證號脫敏
- 車牌號脫敏
- 地址脫敏
- 郵件脫敏
- 密碼脫敏
- 銀行卡號脫敏
/**
* 內置的數據脫敏方式
*/
public class Masks {
/**
* 手機號脫敏
*/
public static final String MOBILE = "mobile";
/**
* 固定電話脫敏
*/
public static final String FIXED_PHONE = "fixed_phone";
/**
* 身份證號脫敏
*/
public static final String ID_CARD_NUMBER = "id_card_number";
/**
* 中文名脫敏
*/
public static final String CHINESE_NAME = "chinese_name";
/**
* 地址脫敏
*/
public static final String ADDRESS = "address";
/**
* 郵件脫敏
*/
public static final String EMAIL = "email";
/**
* 密碼脫敏
*/
public static final String PASSWORD = "password";
/**
* 車牌號脫敏
*/
public static final String CAR_LICENSE = "car_license";
/**
* 銀行卡號脫敏
*/
public static final String BANK_CARD_NUMBER = "bank_card_number";
//...
}
使用示例:
@Table("tb_account")
public class Account {
@Id(keyType = KeyType.Auto)
private Long id;
@ColumnMask(Masks.CHINESE_NAME)
private String userName;
@ColumnMask(Masks.EMAIL)
private String email;
}
如果這些內置的脫敏規則不滿足你的要求的話,你還可以自定義脫敏規則。
多數據源
MyBaits-Flex 內置了功能完善的多數據源支持,無需借助其他第三方插件或者依賴,支持包括 druid、hikaricp、dbcp2、beecp 在內的任何數據源。
Spring 框架下的配置如下(無 Spring 框架的場景下,同樣也可以編碼的形式使用):
mybatis-flex:
datasource:
ds1:
type: druid
url: jdbc:mysql://127.0.0.1:3306/db
username: root
password: 123456
asyncInit: true
ds2:
type: com.your.datasource.type2
url: jdbc:mysql://127.0.0.1:3306/db2
username: root
password: 123456
默認使用第一個配置的數據源,可以通過編碼的方式其他的數據源。
List<Row> rows = DataSourceKey.use("ds2"
, () -> Db.selectAll("tb_account"));
在多租戶等某些場景下,動態的添加新的數據源也是支持的。
FlexDataSource flexDataSource = (FlexDataSource) FlexGlobalConfig
.getDefaultConfig().getConfiguration()
.getEnvironment().getDataSource();
//新的數據源
HikariDataSource newDataSource = new HikariDataSource();
flexDataSource.addDataSource("newKey", newDataSource);
字段加密
字段加密指的是我們從數據庫中取出數據的時候,對其中的一些字段進行加密,這樣返回的內容為加密內容,而非明文內容。
字段加密的功能實現依賴于 MyBatis-Flex 實體類監聽:
public class AccountOnSetListener implements SetListener {
@Override
public Object onSet(Object entity, String property, Object value) {
if (value != null){
//對字段內容進行加密
value = encrypt(value);
}
return value;
}
}
@Table(value = "tb_account", onSet = AccountOnSetListener.class)
public class Account {
@Id(keyType = KeyType.Auto)
private Long id;
private String userName;
private String password;
//getter setter
}
除了字段加密之外,字典回寫、字段權限、字段脫敏等功能的實現都依賴于實體類監聽。
總結
這篇文章我們簡單對比了 MyBatis-Flex 和 MyBatis-Plus ,并對 MyBatis-Flex 的個別核心功能進行了簡單介紹。
更多關于 MyBatis-Flex 的介紹,大家可以去 MyBatis-Flex 的官網看看,地址:https://mybatis-flex.com/ 。
來源:
https://mp.weixin.qq.com/s/wvk_twc-DCURiNiE5njFXA