前几天运营提到说后台管理系统有几个地方想要模糊查询..

 

想了下是简单的,就是要注意以前方法的被调用情况,进行增量改动,以免牵一发而动全身。整理一波记录下(本次案例是按名字模糊查询学生信息)。

三种方式概览

  1. SQL 语句正常 like,service 层按需要添加 '%'
  2. SQL 使用 CONCAT 函数
  3. mybatis 的 bind 语法

依旧使用H2数据库(>>springboot与H2数据库快速本地测试),初始化脚本配置一个简单的学生表,添几条记录。

H2和mybatis相关配置

1)maven依赖

<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.0.1</version>
</dependency>

2)application.properties

server.port=8091
server.servlet.context-path=/tsa
#spring.datasource.url=jdbc:h2:mem:test
spring.datasource.url=jdbc:h2:~/test
spring.datasource.driver-class-name=org.h2.Driver
spring.datasource.username=sa
spring.datasource.password=123456
spring.datasource.schema=classpath:h2sql/schema.sql
spring.datasource.data=classpath:h2sql/data.sql
spring.h2.console.enabled=true
#localhost:8080/projectName/h2-console
spring.h2.console.path=/h2-console
#mybatis.config-location=classpath:/mybatis-config.xml
mybatis.mapper-locations=classpath:/sqlmap/*Mapper.xml
mybatis.configuration.map-underscore-to-camel-case=true
mybatis.type-aliases-package=com.hwc.tsa.bean
logging.level.com.hwc.tsa.dao=debug
logging.level.com.hwc.tsa.mapper=debug

3)H2初始化脚本(学生表)

h2sql/schema.sql

drop table if exists student;
create table student(
id int unsigned not null auto_increment comment '自增主键',
name varchar(20) not null comment '字典类型-关联字段',
age int unsigned not null comment '年龄', status tinyint not null default 1 comment '逻辑删除字段',
crt_time timestamp not null default CURRENT_TIMESTAMP comment '创建时间',
upd_time timestamp default CURRENT_TIMESTAMP on update CURRENT_TIMESTAMP comment '更新时间', PRIMARY KEY (id)
);

h2sql/data.sql

insert into student(name, age) values ('菠萝包', 1);
insert into student(name, age) values ('皮卡丘', 3);
insert into student(name, age) values ('悟空', 35);
insert into student(name, age) values ('悟饭', 21);
insert into student(name, age) values ('克林', 37);
insert into student(name, age) values ('弗利沙', 999);
insert into student(name, age) values ('妙蛙种子', 3);
insert into student(name, age) values ('杰尼龟', 2);
insert into student(name, age) values ('小杰', 17);

启动项目并检查项目结构

本次不是在之前的demo项目上继续的,只需关注几个目标包(xxx.bean.entity,xxx.mapper、resources/sqlmap、resources/h2sql)就OK。

1)先启动springboot项目,初始化H2数据库。

启动项目:

 

控制台连接H2数据库(>>springboot与H2数据库快速本地测试)检查数据初始化:

 

2)建立相应的包和目录结构,使用mybatis逆向工具快速生成entity和mapper

>>简单使用maven-mybatis插件逆向生成entity和Mapper

结构图:

 

方式1

方式1即 SQL 部分只写简单的 like,在 service 层决定哪个字段需要模糊查(加上 '%')。

StudentMapper 新增方法(按名字模糊查):

/**
* 表单模糊查询支持
* @param record
* @return
*/
List<Student> selectByFormLikeSelective(Student record);

StudentMapper.xml 新增查询映射点:

<select id="selectByFormLikeSelective" parameterType="student" resultMap="BaseResultMap">
select <include refid="Base_Column_List"/> from student
<where>
<if test="name!=null and name!=''">
and name like #{name}
</if>
<if test="status!=null">
and status = #{status}
</if>
</where>
</select>

编写测试类:

@RunWith(SpringRunner.class)
//不加载web环境,更快捷测试
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.NONE)
//@SpringBootTest
public class MapperDaoTests {
private static final Logger logger = LoggerFactory.getLogger(MapperDaoTests.class); @Autowired
StudentMapper stuMapper; @Test
public void testStudentMapperLikeSelective() {
//模拟controller输入
Map<String, Object> map = new HashMap<>();
map.put("name", "悟");
Student stu = new Student();
BeanUtil.mapValueCopy2Bean(map, stu);
//模拟service处理
stu.setName("悟");
stu.setName(StringUtil.addLikeStringLR(stu.getName()));//两边加 %
//调用mapper(dao)
List<Student> stuList = stuMapper.selectByFormLikeSelective(stu);
//输出验证 预期2行
logger.info("stuList size is: {}", stuList.size());
}
}

JUnit 测试结果:

 

方式2

方式2则是使用 SQL 的 CONCAT 函数,直接在 SQL 中连接 '%' 。

主流数据库都有 CONCAT 函数,另外 Oracle 还可以使用 || 符号更方便,但是为了通用性,建议使用 CONCAT 函数。

修改方式1中的代码。

test 方法中去掉/注掉加百分号行:

//stu.setName(StringUtil.addLikeStringLR(stu.getName()));//两边加 %

xml 中修改目标 like 处为:

<if test="name!=null and name!=''">
<!-- and name like #{name} -->
and name like concat(concat('%', #{name}), '%')
</if>

测试结果(注意dao传入时是没有加百分号的):

 

方式3

方式3使用 mybatis 动态 sql 的 bind 语法,官方地址:http://www.mybatis.org/mybatis-3/zh/dynamic-sql.html。

这样的好处是既不要改 service 代码,也不需要使用 CONCAT 函数拼接字段值,只需在 sql 语句块开始处定义属性绑定规则即可。

Mapper.xml 修改:

<select id="selectByFormLikeSelective" parameterType="student" resultMap="BaseResultMap">
<bind name="name" value="'%' + _parameter.getName() + '%'" />
select <include refid="Base_Column_List"/> from student
<where>
<if test="name!=null and name!=''">
and name like #{name}
</if>
<if test="status!=null">
and status = #{status}
</if>
</where>
</select>

运行截图:

 

传入就是带百分号的,可以看出,这种方式其实就是方式1,只不过加 '%' 的事情,mybatis 帮我们做了。

总结

这三种方式都很简单,但是综合而讲,直男君推荐方式1,我们在 service 层自行决定哪个需要模糊查。方式2的话,SQL不简洁;方式3则没有通用性。

表单模糊查询的三种简单方式(springboot-h2-mybatis)的更多相关文章

  1. MyBatis模糊查询的三种拼接方式

    1. sql中字符串拼接 SELECT * FROM tableName WHERE name LIKE CONCAT(CONCAT('%', #{text}), '%'); 2. 使用 ${...} ...

  2. MyBatis 模糊查询的 4 种实现方式

    引言 MyBatis 有 4 种方式可以实现模糊查询. 员工信息表 ( tb_employee ) 如下: id name sex email birthday address 001 张一凡 男 z ...

  3. 2019年6月14日 Web框架之Django_07 进阶操作(MTV与MVC、多对多表三种创建方式、前后端传输数据编码格式contentType、ajax、自定义分页器)

    摘要 MTV与MVC 多对多表三种创建方式 ajax ,前后端传输数据编码格式contentType 批量插入数据和自定义分页器 一.MVC与MTV MVC(Model View Controller ...

  4. ASP.NET Core Razor 编辑表单 - ASP.NET Core 基础教程 - 简单教程,简单编程

    原文:ASP.NET Core Razor 编辑表单 - ASP.NET Core 基础教程 - 简单教程,简单编程 ASP.NET Core Razor 编辑表单 上一章节我们介绍了标签助手和 HT ...

  5. MyBatis实现模糊查询的几种方式

    在学习MyBatis过程中想实现模糊查询,可惜失败了.后来上百度上查了一下,算是解决了.记录一下MyBatis实现模糊查询的几种方式. 数据库表名为test_student,初始化了几条记录,如图: ...

  6. jQuery form插件的使用--用 formData 参数校验表单,验证后提交(简单验证).

    Form Plugin API 里提供了很多有用的方法可以让你轻松的处理表单里的数据和表单的提交过程. 测试环境:部署到Tomcat中的web项目. 一.引入依赖js <script src=& ...

  7. mysql中模糊查询的四种用法介绍

    下面介绍mysql中模糊查询的四种用法: 1,%:表示任意0个或多个字符.可匹配任意类型和长度的字符,有些情况下若是中文,请使用两个百分号(%%)表示. 比如 SELECT * FROM [user] ...

  8. mysql进阶(六)模糊查询的四种用法介绍

    mysql中模糊查询的四种用法介绍 这篇文章主要介绍了mysql中模糊查询的四种用法,需要的朋友可以参考下. 下面介绍mysql中模糊查询的四种用法: 1 %: 表示任意0个或多个字符.可匹配任意类型 ...

  9. Django多对多表的三种创建方式,MTV与MVC概念

    MTV与MVC MTV模型(django): M:模型层(models.py) T:templates V:views MVC模型: M:模型层(models.py) V:视图层(views.py) ...

随机推荐

  1. MongoDB与Redis的简单使用

    mongodb 概念解析 SQL术语/概念 MongoDB术语/概念 解释说明 database database 数据库 table collection 数据库表/集合 row document ...

  2. Appium+python自动化(二十五)- 那些让人抓耳挠腮、揪头发和掉头发的事 - 获取控件ID(超详解)

    简介 在前边的第二十二篇文章里,已经分享了通过获取控件的坐标点来获取点击事件的所需要的点击位置,那么还有没有其他方法来获取控件点击事件所需要的点击位置呢?答案是:Yes!因为在不同的大小屏幕的手机上获 ...

  3. Core CLR Host 源码简单分析

    在定制 CLR Host的时候,可以通过调用如下代码,来获取当前需要被宿主的程序调用入口: hr = Host->CreateDelegate( domainId, L"Main,Ve ...

  4. 03-Django模型类

    ORM框架:对象-关系-映射 将面向对象语言程序中的对象自动持久化到关系数据库中.本质就是将数据从一种形式转换到另外一种形式O表示Object 对象类R表示Relations 关系,关系数据库中的表M ...

  5. 数据结构之堆栈java版

    import java.lang.reflect.Array; /* 具体原理在c++版已经说的很清楚,这里不再赘述, 就提一点:java的泛型具有边界效应,一旦离开作用域立马被替换为object类型 ...

  6. Apache 80端口可以访问,8080却不可访问

    RT, 记录一下,后面看是否有解决方案.

  7. Axure 使用 简单入门

    1.Axure 简介 Axure是快速原型工具,简单来说就是把自己的web或app想法快速的展示出来的工具.具体信息百科:https://baike.baidu.com/item/axure%20rp ...

  8. 基于hprose-golang创建RPC微服务

    Hprose(High Performance Remote Object Service Engine) 是一款先进的轻量级.跨语言.跨平台.无侵入式.高性能动态远程对象调用引擎库.它不仅简单易用, ...

  9. 算法与数据结构基础 - 合并查找(Union Find)

    Union Find算法基础 Union Find算法用于处理集合的合并和查询问题,其定义了两个用于并查集的操作: Find: 确定元素属于哪一个子集,或判断两个元素是否属于同一子集 Union: 将 ...

  10. Redhat Linux 系统上安装JDK 1.7

    作者:潇湘隐者 出处:http://www.cnblogs.com/kerrycode/ 步骤1:下载JDK 1.7 安装包  JDK 1.7 下载地址:http://www.oracle.com/t ...