当前位置: 代码网 > it编程>编程语言>Java > MyBatis-Plus 中 的动态SQL 片段(sqlSegment)详解

MyBatis-Plus 中 的动态SQL 片段(sqlSegment)详解

2025年06月30日 Java 我要评论
以下是针对 mybatis-plus 中 通用 sql 片段(sqlsegment) 的清晰详解,结合核心功能与实用场景,逐步说明其用法:一、什么是sqlsegment?在 mybatis-plus

以下是针对 mybatis-plus 中 通用 sql 片段(sqlsegment) 的清晰详解,结合核心功能与实用场景,逐步说明其用法:

一、什么是sqlsegment?

在 mybatis-plus 中,sqlsegment 通常指 动态生成的 sql 代码块,例如由条件构造器(wrapper)自动生成的 where 条件、order by 排序等。开发者可通过特定语法(如 ${ew.customsqlsegment}或者${ew.sqlsegment})将这些片段插入到自定义 sql 中,实现灵活组合。

二、核心使用方式

1.条件构造器(wrapper)动态生成 sql 片段

通过 querywrapperlambdaquerywrapper 构建条件,自动生成 where 后的条件语句。

// 创建 wrapper
querywrapper<user> wrapper = new querywrapper<>();
wrapper.eq("status", 1)
       .like("username", "tom")
       .orderbydesc("create_time");
// 执行查询(自动拼接条件到 sql)
list<user> users = usermapper.selectlist(wrapper);

生成 sql

select * from user 
where status = 1 and username like '%tom%' 
order by create_time desc

2.在 xml 中引用 wrapper 的 sql 片段

使用 ${ew.customsqlsegment} 占位符,将 wrapper 中的条件插入到自定义 sql。

<!-- xml 映射文件 -->
<select id="selectbywrapper" resulttype="user">
    select * from user
    where age > 18
    ${ew.customsqlsegment}  <!-- 插入 wrapper 的条件 -->
</select>

java 调用

querywrapper<user> wrapper = new querywrapper<>();
wrapper.ne("email", null);  // 添加条件:email is not null
list<user> users = usermapper.selectbywrapper(wrapper);

生成 sql

select * from user
where age > 18
  and email is not null  <!-- 来自 wrapper -->

三、关键语法解析

1.${ew.customsqlsegment}的作用

  • ew 是 mybatis-plus 的固定参数名,代表 wrapper 对象。
  • customsqlsegmentwrapper 中生成的 sql 片段(如 where 条件、order by)。
  • 注意:必须确保 wrapper 对象作为参数传递到 xml 中(通常参数名为 ew)。

2.lambda 表达式避免硬编码字段名

使用 lambdaquerywrapper 提升代码安全性和可读性:

lambdaquerywrapper<user> lambdawrapper = new lambdaquerywrapper<>();
lambdawrapper.eq(user::getstatus, 1)         // 方法引用代替字符串
             .ge(user::getage, 18)
             .orderbyasc(user::getcreatetime);

3.${ew.customsqlsegment} 与 ${ew.sqlsegment} 的区别对比

‌1.${ew.customsqlsegment}‌:‌动态拼接完整 where 条件‌:常用于无需手动编写 where 的自定义 sql 中

2.‌${ew.sqlsegment}‌:‌仅注入条件表达式‌:需手动拼接 where,适用于需要精确控制 sql 结构的场景

// mapper 接口  
@select("select * from user ${ew.customsqlsegment}")  
list<user> selectpagecustom(@param(constants.wrapper) wrapper<user> wrapper);  
@select("select * from user where ${ew.sqlsegment}")  
list<user> selectpagewhere(@param(constants.wrapper) wrapper<user> wrapper);  

四、实际应用场景

场景 1:动态条件查询

根据用户输入动态拼接查询条件,无需手动编写 if 判断。

public list<user> searchusers(string name, integer minage) {
    lambdaquerywrapper<user> wrapper = new lambdaquerywrapper<>();
    wrapper.like(stringutils.isnotblank(name), user::getusername, name)
           .ge(minage != null, user::getage, minage);
    return usermapper.selectlist(wrapper);
}
  • likege 方法中的第一个参数为条件布尔值,自动决定是否拼接该条件。

场景 2:复用公共 sql 片段

在 xml 中定义公共片段,结合 wrapper 实现复用。

<!-- 定义公共的 where 条件 -->
<sql id="activeuser">
    is_deleted = 0 and status = 'active'
</sql>
<!-- 在查询中复用 -->
<select id="selectactiveusers" resulttype="user">
    select * from user
    where <include refid="activeuser"/>
    ${ew.customsqlsegment}  <!-- 追加其他动态条件 -->
</select>

java 调用

querywrapper<user> wrapper = new querywrapper<>();
wrapper.like("username", "admin");
list<user> users = usermapper.selectactiveusers(wrapper);

生成 sql

select * from user
where is_deleted = 0 and status = 'active'  <!-- 公共片段 -->
  and username like '%admin%'              <!-- 动态条件 -->

场景 3:逻辑删除自动过滤

配置 mybatis-plus 全局逻辑删除,自动在所有查询中注入 where is_deleted=0

# application.yml
mybatis-plus:
  global-config:
    db-config:
      logic-delete-field: isdeleted   # 实体类字段名
      logic-delete-value: 1           # 删除后的值
      logic-not-delete-value: 0       # 未删除的值
  • 无需手动编写条件,删除操作自动变为 update 语句,查询自动过滤已删除数据。

五、最佳实践与避坑指南

1.优先使用 lambdaquerywrapper

  • 优势:避免字段名硬编码,编译时检查,重构友好。
  • 示例
    lambdawrapper.eq(user::getstatus, 1)  // 正确性由编译器保证

2.谨慎使用${}防止 sql 注入

  • 安全写法
    where username = #{param}    <!-- 使用 #{} 预编译 -->
  • 风险写法
    order by ${orderby}          <!-- 直接拼接字符串,需手动过滤参数 -->

3.复杂 sql 结合 xml 片段

对于多表 join 或复杂统计,仍可在 xml 中编写完整 sql,利用 <include> 复用片段。

<select id="selectuserwithrole" resulttype="map">
    select u.*, r.role_name 
    from user u
    left join role r on u.role_id = r.id
    ${ew.customsqlsegment}
</select>

六、总结

  • 核心机制:通过 wrapper 生成动态 sql 片段,结合 ${ew.customsqlsegment} 嵌入自定义 sql。
  • 适用场景:动态条件查询、逻辑删除、多租户隔离、公共代码复用。
  • 优势:减少重复代码、提升可维护性、保持 sql 灵活性。

通过合理利用 mybatis-plus 的 sql 片段功能,可显著简化开发流程,尤其适合快速迭代的中大型项目。

到此这篇关于mybatis-plus 中 的动态sql 片段(sqlsegment)讲解的文章就介绍到这了,更多相关mybatis-plus动态sql内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com