MyBatis性能提升100倍的ORM框架 -- 知识铺
开源项目简介
bean-searcher 是一款比 MyBatis 效率快 100 倍的条件检索引擎,专注高级查询的只读 ORM,天生支持联表,免 DTO/VO 转换,使一行代码实现复杂列表检索成为可能!
开源协议
使用Apache-2.0开源协议
界面展示
Bean Searcher 功能介绍
特性
-
实体多表映射
-
动态字段运算符
-
分组聚合查询
-
Select | Where | From 子查询
-
实体类嵌入参数
-
字段转换器
-
Sql 拦截器
-
数据库 Dialect 扩展
-
多数据源与动态数据源
-
注解缺省与自定义
-
字段运算符扩展
快速开发
使用 Bean Searcher 可以极大节省后端的复杂列表检索接口的开发时间。
集成简单
可以和任意 Java Web 框架集成,如:SpringBoot、Grails、Jfinal 等。
扩展性强
面向接口设计,用户可自定义扩展 Bean Searcher 中的任何组件。
支持注解缺省
约定优于配置,可省略注解,可复用原有域类,同时支持自定义注解。
支持多数据源
分库分表?在这里特别简单,告别分库分表带来的代码熵值增高问题。
支持Select指定字段
同一个实体类,可指定只Select其中的某些字段,或排除某些字段。
支持参数过滤器
支持添加多个参数过滤器,可自定义参数过滤规则。
支持字段转换器
支持添加多个字段转换器,可自定义数据库字段到实体类字段的转换规则。
支持SQL拦截器
支持添加多个 SQL 拦截器,可自定义 SQL 生成规则。
技术选型
框架目的
只一行代码实现:多表联查分页搜索任意字段组合过滤任意字段排序多字段统计。
架构图
aaaaaaa虽然诸如Hibernate、MyBatis以及Spring Data JDBC等ORM工具在处理增删改操作时表现出色,但在面对复杂的查询需求,尤其是涉及多条件筛选、联表操作、分页及排序的列表查询时,则显得不够灵活。传统ORM框架通常需要编写较多的代码来实现这样的功能,增加了开发复杂度。
Bean Searcher则专注于简化这类复杂的查询过程,通过其强大的特性,开发者能够以极其简洁的方式——几乎仅需一行代码——完成上述提到的所有查询需求。
例如,考虑一个典型应用场景,其中涉及到对数据库执行包含多个过滤条件、跨表关联、结果分页以及特定字段排序的操作。使用Bean Searcher,可以非常高效地构造出满足这些要求的查询语句,极大地提升了开发效率和代码可维护性。
后端需要写一个检索接口,而如果用传统的 ORM 来写,代码之复杂是可以想象的。
而 Bean Searcher 却可以:
只一行代码实现以上功能
首先,你有一个实体类:
@SearchBean(tables="user u, role r", joinCond="u.role_id = r.id", autoMapTo="u")
public class User {
private long id;
private String username;
private int status;
private int age;
private String gender;
private Date joinDate;
private int roleId;
@DbField("r.name")
private String roleName;
// Getters and setters...
}
然后你就可以用一行代码实现这个用户检索接口:
@RestController
@RequestMapping("/user")
public class UserController {
@Autowired
private BeanSearcher beanSearcher; // 注入 BeanSearcher 的检索器
@GetMapping("/index")
public SearchResult<User> index(HttpServletRequest request) {
// 这里只写一行代码
return beanSearcher.search(User.class, MapUtils.flat(request.getParameterMap()), new String[]{ "age" });
}
}
这一行代码实现了以下功能:
-
多表联查
-
分页搜索
-
组合过滤
-
任意字段排序
-
字段统计
例如,该接口支持如下请求:
-
GET: /user/index
无参请求(默认分页):
{
"dataList": [
{
"id": 1,
"username": "Jack",
"status": 1,
"level": 1,
"age": 25,
"gender": "Male",
"joinDate": "2021-10-01"
},
... // 默认返回 15 条数据
],
"totalCount": 100,
"summaries": [
2500 // age 字段统计
]
}
```
aaaaaaa 下面是用户查询接口 `/user/index` 的使用示例,包括分页、过滤、排序和字段选择功能。
### 分页查询
- **请求**:`GET: /user/index?page=1&size=10`
- **说明**:通过指定 `page` 和 `size` 参数来获取第一页的10条用户记录。
### 按状态过滤
- **请求**:`GET: /user/index?status=1`
- **说明**:返回所有状态为 `1` 的用户列表。
### 模糊搜索用户名
- **请求**:`GET: /user/index?name=Jac&name-op=sw`
- **说明**:查找用户名以 `Jac` 开头的所有用户。这里 `name-op=sw` 表示搜索模式为以给定值开头。
### 忽略大小写匹配用户名
- **请求**:`GET: /user/index?name=Jack&name-ic=true`
- **说明**:返回用户名等于 `Jack` 的用户,且此搜索忽略字母的大小写。
### 根据年龄降序排列
- **请求**:`GET: /user/index?sort=age&order=desc`
- **说明**:用户列表将按照 `age` 字段进行降序排列。
### 选择特定字段
- **请求**:`GET: /user/index?onlySelect=username,age`
- **说明**:仅检索用户的 `username` 和 `age` 两个字段。
{
“dataList”: [
{
“username”: “Jack”,
“age”: 25
},
…
],
“totalCount”: 100,
“summaries”: [
2500
]
}
```
-
GET: /user/index? selectExclude=joinDate
检索时排除 joinDate 字段
参数构建器
Map<String, Object> params = MapUtils.builder()
.selectExclude(User::getJoinDate) // 排除 joinDate 字段
.field(User::getStatus, 1) // 过滤:status = 1
.field(User::getName, "Jack").ic() // 过滤:name = 'Jack' (case ignored)
.field(User::getAge, 20, 30).op(Opetator.Between) // 过滤:age between 20 and 30
.orderBy(User::getAge, "asc") // 排序:年龄,从小到大
.page(0, 15) // 分页:第 0 页, 每页 15 条
.build();
List<User> users = beanSearcher.searchList(User.class, params);
使用 Bean Searcher 可以极大地节省后端的复杂列表检索接口的开发时间!普通的复杂列表查询只需一行代码,单表检索可复用原有 Domain,无需定义 SearchBean。可以和任意 Java Web 框架集成,如:SpringBoot、Spring MVC、Grails、Jfinal 等等。Spring Boot 项目,添加依赖即集成完毕。
implementation 'com.ejlchina:bean-searcher-boot-stater:3.6.0'
接着便可在 Controller 或 Service 里注入检索器:
/**
* 注入 Map 检索器,它检索出来的数据以 Map 对象呈现
*/
@Autowired
private MapSearcher mapSearcher;
/**
* 注入 Bean 检索器,它检索出来的数据以 泛型 对象呈现
*/
@Autowired
private BeanSearcher beanSearcher;
其它框架,使用如下依赖:
implementation 'com.ejlchina:bean-searcher:3.6.0'
然后可以使用 SearcherBuilder 构建一个检索器:
DataSource dataSource = ... // 拿到应用的数据源
// DefaultSqlExecutor 也支持多数据源
SqlExecutor sqlExecutor = new DefaultSqlExecutor(dataSource);
// 构建 Map 检索器
MapSearcher mapSearcher = SearcherBuilder.mapSearcher()
.sqlExecutor(sqlExecutor)
.build();
// 构建 Bean 检索器
BeanSearcher beanSearcher = SearcherBuilder.beanSearcher()
.sqlExecutor(sqlExecutor)
.build();
Bean Searcher 特性介绍
扩展性强
Bean Searcher 支持高度的自定义和扩展,允许用户根据需求修改和扩展其组件。以下是一些可以自定义的组件:
-
自定义
FieldOp
: 支持更多字段运算符。 -
自定义
FieldConvertor
: 支持任意特殊字段类型。 -
自定义
DbMapping
: 实现自定义注解或让 Bean Searcher 识别其他 ORM 的注解。 -
自定义
ParamResolver
: 支持其他形式的检索参数。 -
自定义
Dialect
: 支持更多数据库。 此外,Bean Searcher 还提供了丰富的扩展点,以满足不同场景下的需求。
源码地址
Bean Searcher 的源码托管在 Gitee 和 GitHub 上,方便用户查看和下载。 Gitee 地址: https://gitee.com/ejlchina-zhxu/bean-searcher GitHub 地址: https://github.com/ejlchina/bean-searcher 请根据您的需求选择合适的版本进行下载和使用。
<section data-tool="mdnice编辑器" data-website="https://www.mdnice.com"><img data-fileid="100015743" data-imgfileid="100074991" data-ratio="0.08658008658008658" data-type="gif" data-w="462" data-width="100%" data-src="https://cdn.jsdelivr.net/gh/zshipu/imagesv3/2024/202409301106676.gif" data-original-style="-webkit-tap-highlight-color: transparent;outline: 0px;background-size: 16px;border-radius: 8px;font-family: -apple-system, BlinkMacSystemFont, "Helvetica Neue", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei UI", "Microsoft YaHei", Arial, sans-serif;letter-spacing: 0.544px;word-spacing: 2px;display: block;visibility: visible !important;width: 577.969px !important;" data-index="6" src="https://cdn.jsdelivr.net/gh/zshipu/imagesv3/2024/202409301106050.gif" _width="487px" data-order="0" alt="图片" data-fail="0"></section><pre><pre><pre data-style="letter-spacing: 0.544px; font-size: 16px; color: rgb(63, 63, 63); word-spacing: 1px; line-height: inherit;"><section powered-by="xiumi.us" data-darkmode-bgcolor="rgb(36, 36, 36)" data-darkmode-original-bgcolor="rgb(255, 255, 255)" data-darkmode-color="rgb(230, 230, 230)" data-darkmode-original-color="rgb(0, 0, 0)" data-style="margin-right: 0.5em; margin-left: 0.5em; white-space: normal; font-family: -apple-system-font, system-ui, "Helvetica Neue", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei UI", "Microsoft YaHei", Arial, sans-serif; color: rgb(0, 0, 0); letter-spacing: 0px; word-spacing: 2px;" data-mpa-template-id="1250" data-mpa-color="#ffffff" data-mpa-category="divider"><p data-darkmode-bgcolor="rgb(36, 36, 36)" data-darkmode-original-bgcolor="rgb(255, 255, 255)" data-darkmode-color="rgb(106, 104, 111)" data-darkmode-original-color="rgb(106, 104, 111)">1. <a target="_blank" href="http://mp.weixin.qq.com/s?__biz=MzI4Njc5NjM1NQ==&mid=2247548979&idx=2&sn=7959fff68b2601e9919acb696cf1737e&chksm=ebd53f1fdca2b6093dfd60ed849e5564b06f57fab36ff356e1eb223848cb6a38882946aaa102&scene=21#wechat_redirect" textvalue="Java面试题精选阶段汇总,已更新450期~" linktype="text" imgurl="" imgdata="null" data-itemshowtype="0" tab="innerlink" data-linktype="2" hasload="1">Java面试题精选阶段汇总,已更新450期~</a></p><p data-darkmode-bgcolor="rgb(36, 36, 36)" data-darkmode-original-bgcolor="rgb(255, 255, 255)" data-darkmode-color="rgb(138, 138, 138)" data-darkmode-original-color="rgb(89, 89, 89)">2. <a target="_blank" href="http://mp.weixin.qq.com/s?__biz=MzU2MTI4MjI0MQ==&mid=2247535089&idx=1&sn=4c0a302c95a2223bd61e1b6277b7f626&chksm=fc79245fcb0ead495ee37e63f02e2c3741fd68db81f9b5e3281df13e89a0037a3a92e860a473&scene=21#wechat_redirect" textvalue="推荐一款精美、高质量、开源的问卷系统" linktype="text" imgurl="" imgdata="null" data-itemshowtype="0" tab="innerlink" data-linktype="2" hasload="1">推荐一款精美、高质量、开源的问卷系统</a></p><p data-darkmode-bgcolor="rgb(36, 36, 36)" data-darkmode-original-bgcolor="rgb(255, 255, 255)" data-darkmode-color="rgb(138, 138, 138)" data-darkmode-original-color="rgb(89, 89, 89)">3. <a target="_blank" href="http://mp.weixin.qq.com/s?__biz=MzU2MTI4MjI0MQ==&mid=2247533655&idx=1&sn=471b46bf484932a70497aed11aa27b5e&chksm=fc7929f9cb0ea0ef1deeea27d190a8e65cb0da408f8230060e17a8dec412c2401c72ba0be595&scene=21#wechat_redirect" textvalue="一款高颜值、开源的物联网一体化平台" linktype="text" imgurl="" imgdata="null" data-itemshowtype="0" tab="innerlink" data-linktype="2" hasload="1">一款高颜值、开源的物联网一体化平台</a></p><p data-darkmode-bgcolor="rgb(36, 36, 36)" data-darkmode-original-bgcolor="rgb(255, 255, 255)" data-darkmode-color="rgb(106, 104, 111)" data-darkmode-original-color="rgb(106, 104, 111)">4. <a target="_blank" href="http://mp.weixin.qq.com/s?__biz=MzI4Njc5NjM1NQ==&mid=2247556937&idx=1&sn=12a994542329d093b5d07ccd43371436&chksm=ebd52065dca2a973e62733cbcf1e381ae0a49c5886d157afecb5dddd0d559023e02d95d1943d&scene=21#wechat_redirect" textvalue="18 个一线工作中常用 Shell 脚本【实用版】" linktype="text" imgurl="" imgdata="null" data-itemshowtype="0" tab="innerlink" data-linktype="2" hasload="1">18 个一线工作中常用 Shell 脚本【实用版】</a></p></section></pre></pre></pre>
PS:因公众号平台更改了推送规则,如果不想错过内容,记得读完点一下**“在看”,加个“星标”**,这样每次新文章推送才会第一时间出现在你的订阅列表里。
<p data-tool="mdnice编辑器">点<strong>“在看”</strong>支持我们,共同成长</p>
- 原文作者:知识铺
- 原文链接:https://index.zshipu.com/geek002/post/20240918/MyBatis%E6%80%A7%E8%83%BD%E6%8F%90%E5%8D%87100%E5%80%8D%E7%9A%84ORM%E6%A1%86%E6%9E%B6--%E7%9F%A5%E8%AF%86%E9%93%BA/
- 版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议进行许可,非商业转载请注明出处(作者,原文链接),商业转载请联系作者获得授权。
- 免责声明:本页面内容均来源于站内编辑发布,部分信息来源互联网,并不意味着本站赞同其观点或者证实其内容的真实性,如涉及版权等问题,请立即联系客服进行更改或删除,保证您的合法权益。转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达。也可以邮件至 sblig@126.com