mybatis-plus条件构造器
Posted 唐微港
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了mybatis-plus条件构造器相关的知识,希望对你有一定的参考价值。
条件构造器
Wrapper
介绍
如图所示mybatis-plus平时可以使用的类有
LambdaQueryWrapper,LambdaUpdateWrapper,QueryWrapper,UpdateWrapper,他们的继承实现关系如下。
Wrapper(抽象类abstract)
AbstractWrapper(抽象类abstract)
AbstractLambdaWrapper(抽象类abstract)
LambdaQueryWrapper(可用类)
LambdaUpdateWrapper (可用类)
QueryWrapper (可用类)
UpdateWrapper(可用类)
详细介绍
- Wrapper : 条件构造抽象类,最顶端的父类
- AbstractWrapper : 用于查询条件封装,生成 sql 的 where 条件
- AbstractLambdaWrapper : Lambda 语法使用,可以使用 lambda表达式方式 获取 column。
- LambdaQueryWrapper :用于Lambda语法表达式做查询时的Wrapper
- LambdaUpdateWrapper : 用于更新时使用Lambda表达式更新的Wrapper
- QueryWrapper : Entity 对象查询时封装的wrapper,不使用lambda语法
- UpdateWrapper : Update 更新时封装的wrapper,用于Entity对象更新,不使用lambda语法
链式调用
链式调用就是连续调的意思,例如象下面这种.isNull().ge().isNotNull();这种方式就是链式调用
//链式调用方式
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper
.isNull("name")
.ge("age", 12)
.isNotNull("email");
mapper.selectList(queryWrapper);
//对应链式调用会执行的SQL
select xxx,xxx,... from xx where age >= 12 and name is null and email is not null;
演示实例
这里的mapper要是直接或间接继承了mybatis-plus中的IaseMapper或者IaseService后才能使用,当然运用spring 注入的方式也可以
QueryWrapper
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper
.isNull("name")
.ge("age", 12)
.isNotNull("email");
mapper.delete(queryWrapper);
UpdateWrapper
//根据id更新指定字段,设置更新的字段为set
UpdateWrapper<AssetBaseInfo> updateWrapper = new UpdateWrapper<>();
updateWrapper.set("company_id", assetTransferDetails.getCompanyId());
updateWrapper.set("department_id", assetTransferDetails.getDepartmentId());
updateWrapper.set("user_id", assetTransferDetails.getUserId());
updateWrapper.set("asset_location", assetTransferDetails.getTransferLocation());
updateWrapper.eq("id", assetId);
assetBaseInfoService.update(updateWrapper);
LambdaQueryWrapper
使用Lambda的方式直接根据实体类对应的get方法的方式就可以解析成数据表字段的方式
//User::getName方式就和直接填写表字段name一样
LambdaQueryWrapper<User>() lambdaqw = new LambdaQueryWrapper<User>()
.eq(User::getName, "lambda")
.gt(User::getAge, user.getApge()
baseMapper.selectList(user, lambdaqw));
LambdaUpdateWrapper
使用Lambda的方式直接根据实体类对应的get方法的方式就可以解析成数据表的字段的方式
LambdaUpdateWrapper<User>() lambdaqw = new LambdaUpdateWrapper<User>()
.eq(User::getName, "lambda")
.eq(User::getAge, user.getApge()
baseMapper.update(user, lambdaqw));
Lambda转化
QueryWrapper和UpdateWrapper也可以通过使用.lambda()的方式达到和LambdaQueryWrapper,LambdaUpdateWrapper一样的效果。
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper
.lambda()
.isNull(User::getName)
.ge(User:getAge, 12)
mapper.selectList(queryWrapper);
条件
警告: 不支持以及不赞成在 RPC 调用中把 Wrapper 进行传输
注意:
- —>表示对该知识点进行说明
- Object val表示需要传入的值
- boolean condition 表示条件,比如 xxx != null
- R column 表示要操作对应的表字段
allEq
类似于多个eq()
allEq(Map<R, V> params)
allEq(Map<R, V> params, boolean null2IsNull)
allEq(boolean condition, Map<R, V> params, boolean null2IsNull)
参数说明:
params
:key
为数据库字段名,value
为字段值
null2IsNull
: 为true
则在map
的value
为null
时调用 isNull 方法,为false
时则忽略value
为null
的
- 例1:
allEq({id:1,name:"老王",age:null})
—>id = 1 and name = '老王' and age is null
- 例2:
allEq({id:1,name:"老王",age:null}, false)
—>`id = 1 and name = ‘老王’
allEq(BiPredicate<R, V> filter, Map<R, V> params)
allEq(BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull)
allEq(boolean condition, BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull)
参数说明:
filter
: 过滤函数,是否允许字段传入比对条件中
params
与null2IsNull
: 同上
- 例1:
allEq((k,v) -> k.indexOf("a") >= 0, {id:1,name:"老王",age:null})
—>name = '老王' and age is null
- 例2:
allEq((k,v) -> k.indexOf("a") >= 0, {id:1,name:"老王",age:null}, false)
—>name = '老王'
eq
eq(R column, Object val)eq(boolean condition, R column, Object val)
- 等于 =
- 例:
eq("name", "老王")
—>name = '老王'
ne
ne(R column, Object val)ne(boolean condition, R column, Object val)
- 不等于 <>
- 例:
ne("name", "老王")
—>name <> '老王'
gt
gt(R column, Object val)gt(boolean condition, R column, Object val)
- 大于 >
- 例:
gt("age", 18)
—>age > 18
ge
ge(R column, Object val)ge(boolean condition, R column, Object val)
- 大于等于 >=
- 例:
ge("age", 18)
—>age >= 18
lt
lt(R column, Object val)lt(boolean condition, R column, Object val)
- 小于 <
- 例:
lt("age", 18)
—>age < 18
le
le(R column, Object val)le(boolean condition, R column, Object val)
- 小于等于 <=
- 例:
le("age", 18)
—>age <= 18
between
between(R column, Object val1, Object val2)between(boolean condition, R column, Object val1, Object val2)
- BETWEEN 值1 AND 值2
- 例:
between("age", 18, 30)
—>age between 18 and 30
notBetween
notBetween(R column, Object val1, Object val2)notBetween(boolean condition, R column, Object val1, Object val2)
- NOT BETWEEN 值1 AND 值2
- 例:
notBetween("age", 18, 30)
—>age not between 18 and 30
like
like(R column, Object val)like(boolean condition, R column, Object val)
- LIKE ‘%值%’
- 例:
like("name", "王")
—>name like '%王%'
notLike
notLike(R column, Object val)notLike(boolean condition, R column, Object val)
- NOT LIKE ‘%值%’
- 例:
notLike("name", "王")
—>name not like '%王%'
likeLeft
likeLeft(R column, Object val)likeLeft(boolean condition, R column, Object val)
- LIKE ‘%值’
- 例:
likeLeft("name", "王")
—>name like '%王'
likeRight
likeRight(R column, Object val)likeRight(boolean condition, R column, Object val)
- LIKE ‘值%’
- 例:
likeRight("name", "王")
—>name like '王%'
isNull
isNull(R column)isNull(boolean condition, R column)
- 字段 IS NULL
- 例:
isNull("name")
—>name is null
isNotNull
isNotNull(R column)isNotNull(boolean condition, R column)
- 字段 IS NOT NULL
- 例:
isNotNull("name")
—>name is not null
in
in(R column, Collection<?> value)in(boolean condition, R column, Collection<?> value)
- 字段 IN (value.get(0), value.get(1), …)
- 例:
in("age",{1,2,3})
—>age in (1,2,3)
in(R column, Object... values)in(boolean condition, R column, Object... values)
- 字段 IN (v0, v1, …)
- 例:
in("age", 1, 2, 3)
—>age in (1,2,3)
notIn
notIn(R column, Collection<?> value)notIn(boolean condition, R column, Collection<?> value)
- 字段 NOT IN (value.get(0), value.get(1), …)
- 例:
notIn("age",{1,2,3})
—>age not in (1,2,3)
notIn(R column, Object... values)notIn(boolean condition, R column, Object... values)
- 字段 NOT IN (v0, v1, …)
- 例:
notIn("age", 1, 2, 3)
—>age not in (1,2,3)
exists
exists(String existsSql)exists(boolean condition, String existsSql)
- 拼接 EXISTS ( sql语句 )
- 例:
exists("select id from table where age = 1")
—>exists (select id from table where age = 1)
notExists
notExists(String notExistsSql)notExists(boolean condition, String notExistsSql)
- 拼接 NOT EXISTS ( sql语句 )
- 例:
notExists("select id from table where age = 1")
—>not exists (select id from table where age = 1)
inSql
这个和in的区别主要就在于这里可以在查询列里面使用sql语句
inSql(R column, String inValue)inSql(boolean condition, R column, String inValue)
- 例:
inSql("age", "1,2,3,4,5,6")
—>age in (1,2,3,4,5,6)
- 例:
inSql("id", "select id from table where id < 3")
—>id in (select id from table where id < 3)
notInSql
这个和notin的区别主要就在于这里可以在查询列里面使用sql语句
notInSql(R column, String inValue)notInSql(boolean condition, R column, String inValue)
- 字段 NOT IN ( sql语句 )
- 例:
notInSql("age", "1,2,3,4,5,6")
—>age not in (1,2,3,4,5,6)
- 例:
notInSql("id", "select id from table where id < 3")
—>id not in (select id from table where id < 3)
groupBy
groupBy(R... columns)groupBy(boolean condition, R... columns)
- 分组:GROUP BY 字段
- 例1:
groupBy("id", "name")
—>group by id,name
- 例2:
groupBy(id!=null,"id", "name")
—>group by id,name
orderByAsc
orderByAsc(R... columns)orderByAsc(boolean condition, R... columns)
- 排序:ORDER BY 字段, … ASC
- 例1:
orderByAsc("id", "name")
—>order by id ASC,name ASC
- 例2:
orderByAsc(id!=null,"id", "name")
—>order by id ASC,name ASC
orderByDesc
orderByDesc(R... columns)orderByDesc(boolean condition, R... columns)
- 排序:ORDER BY 字段, … DESC
- 例1:
orderByDesc("id", "name")
—>order by id DESC,name DESC
- 例2:
orderByDesc(id!=null,"id", "name")
—>order by id DESC,name DESC
orderBy
orderBy(boolean condition, boolean isAsc, R... columns)
- 排序:ORDER BY 字段
- 例:
orderBy(true, true, "id", "name")
—>order by id ASC,name ASC
having
having(String sqlHaving, Object... params)having(boolean condition, String sqlHaving, Object... params)
- HAVING ( sql语句 )
- 例:
having("sum(age) > 10")
—>having sum(age) > 10
- 例:
having("sum(age) > {0}", 11)
—>having sum(age) > 11
func
func(Consumer<Children> consumer)func(boolean condition, Consumer<Children> consumer)
- func 方法(主要方便在出现if…else下调用不同方法能不断链)
- 例:
func(i -> if(true) {i.eq("id", 1)} else {i.ne("id", 1)})
or
or()or(boolean condition)
-
拼接 OR
注意事项:
主动调用
or
表示紧接着下一个方法不是用and
连接!(不调用or
则默认为使用and
连接) -
例:
eq("id",1).or().eq("name","老王")
—>id = 1 or name = '老王'
or(Consumer<Param> consumer)or(boolean condition, Consumer<Param> consumer)
- OR 嵌套
- 例:
or(i -> i.eq("name", "李白").ne("status", "活着"))
—>or (name = '李白' and status <> '活着')
and
and(Consumer<Param> consumer)and(boolean condition, Consumer<Param> consumer)
- AND 嵌套
- 例:
and(i -> i.eq("name", "李白").ne("status", "活着"))
—>and (name = '李白' and status <> '活着')
nested
主要作用就是嵌套拼接条件
nested(Consumer<Param> consumer)nested(boolean condition, Consumer<Param> consumer)
- 正常嵌套 不带 AND 或者 OR
- 例:
nested(i -> i.eq("name", "李白").ne("status", "活着"))
—>(name = '李白' and status <> '活着')
apply
apply(String applySql, Object... params)apply(boolean condition, String applySql, Object... params)
-
拼接 sql
注意事项:
该方法可用于数据库函数 动态入参的
params
对应前面applySql
内部的{index}
部分.这样是不会有sql注入风险的,反之会有! -
例:
apply("id = 1")
—>id = 1
-
例:
apply("date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
—>date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
-
例:
apply("date_format(dateColumn,'%Y-%m-%d') = {0}", "2008-08-08")
—>date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
last
last(String lastSql)last(boolean condition, String lastSql)
-
无视优化规则直接拼接到 sql 的最后
注意事项:
只能调用一次,多次调用以最后一次为准 有sql注入的风险,请谨慎使用
-
例: last(“limit 1”)
以上是关于mybatis-plus条件构造器的主要内容,如果未能解决你的问题,请参考以下文章
mybatis-plus条件构造器以及QueryWrapper用法学习
每天玩转3分钟 MyBatis-Plus - 4. 高级查询(条件构造器)
每天玩转3分钟 MyBatis-Plus - 3. 高级查询(条件构造器)
mybatis-plus条件构造器以及QueryWrapper用法学习