mybatis plus条件拼接
条件构造器
案例table
AbstractWrapper
allEq:全部eq(或个别isNull)
eq:等于 =
ne:不等于 <>
gt:大于 >
ge:大于等于 >=
lt:小于 <
le:小于等于 <=
between:BETWEEN 值1 AND 值2
notBetween:NOT BETWEEN 值1 AND 值2
like:LIKE '%值%'
notLike:NOT LIKE '%值%'
likeLeft:LIKE '%值'
likeRight:LIKE '值%'
isNull:字段 IS NULL
isNotNull: 字段 IS NULL
in:字段 IN
notIn:字段 NOT IN
inSql:字段 IN ( sql语句 )
notInSql:字段 NOT IN ( sql语句 )
groupBy:分组:GROUP BY 字段, ...
orderByAsc:排序:ORDER BY 字段, ... ASC
orderByDesc 排序:ORDER BY 字段, ... DESC
orderBy:排序:ORDER BY 字段, ...
having:HAVING ( sql语句 )
or:拼接 OR
and:AND 嵌套
nested:正常嵌套 不带 AND 或者 OR
apply:拼接 sql
last:无视优化规则直接拼接到 sql 的最后
exists:拼接 EXISTS ( sql语句 )
notExists:拼接 NOT EXISTS ( sql语句 )
QueryWrapper(select)
select:设置查询字段
excludeColumns:排除查询字段
UpdateWrapper(update)
set
setSql:设置 SET 部分 SQL
lambda
使用 Wrapper 自定义SQL
Service.java
方案一 注解方式 Mapper.java
方案二 XML形式 Mapper.xml
分页查询
自定义SQL查询分页数据
热部署(已过时)
逻辑删除(不建议使用)
配置
使用
枚举
配置
实现 IEnum 接口
使用
mybatis plus条件拼接 条件构造器来源: mybatis plus官网
案例table以下出现的第一个入参
说明
:boolean condition
表示该条件是否加入最后生成的sql中没有标明condition
的方法,默认为true
以下出现的泛型Param
均为Wrapper
的子类实例(均具有AbstractWrapper
的所有方法)以下方法在入参中出现的R
为泛型,在普通wrapper中是String
,在LambdaWrapper中是函数(例:Entity::getId
,Entity
为实体类,getId
为字段id
的getMethod)参数R column
均表示数据库字段
,而不是实体类数据字段名!!!(字段名是数据库关键字的自己用转义符包裹!)!以下举例均为使用普通wrapper,入参为Map
和List
的均以json
形式表现!使用中如果入参的Map
或者List
为空,则不会加入最后生成的sql中!!!有任何疑问就点开源码看,看不懂函数的点击我学习新知识wrapper 很重传输 wrapper 可以类比为你的 controller 用 map 接收值(开发一时爽,维护火葬场)正确的 RPC 调用姿势是写一个 DTO 进行传输,被调用方再根据 DTO 执行相应的 *** 作我们拒绝接受任何关于 RPC 传输 Wrapper 报错相关的 issue 甚至 pr
警告
:
不支持以及不赞成在 RPC 调用中把 Wrapper 进行传输(远程调用)
CREATE TABLE `aaa_bbb_cc` (
`ID` int(10) NOT NULL AUTO_INCREMENT,
`aa_as` varchar(255) DEFAULT NULL,
`ab_AAA` varchar(255) DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=18 DEFAULT CHARSET=utf8;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AaaBbbCc implements Serializable {
private static final long serialVersionUID = 1L;
@TableId(value = "ID", type = IdType.AUTO)
private Integer id;
private String aaAs;
@TableField("ab_AAA")
private String abAaa;
}
AbstractWrapper
allEq:全部eq(或个别isNull)说明:
QueryWrapper(LambdaQueryWrapper) 和 UpdateWrapper(LambdaUpdateWrapper) 的父类
用于生成 sql 的 where 条件, entity 属性也用于生成 sql 的 where 条件
注意: entity 生成的 where 条件与 使用各个 api 生成的 where 条件没有任何关联行为
allEq(Map params)
allEq(Map params, boolean null2IsNull)
allEq(boolean condition, Map params, boolean null2IsNull)
allEq(BiPredicate filter, Map params)
allEq(BiPredicate filter, Map params, boolean null2IsNull)
allEq(boolean condition, BiPredicate filter, Map params, boolean null2IsNull)
参数说明:params
: key
为数据库字段名(注意不是entity),value
为字段值null2IsNull
: 为true
则在map
的value
为null
时调用 isNull 方法,为false
时则忽略value
为null
的filter
: 过滤函数,是否允许字段传入比对条件中
案例
Map stringTMap=new LinkedHashMap<>();
stringTMap.put("ID",12 );
stringTMap.put("aa_as",null);
queryWrapper.allEq(stringTMap);//ID = ? AND aa_as IS NULL :null的直接is null
queryWrapper.allEq(stringTMap,false);// WHERE ID = ? :null的不查询
queryWrapper.allEq(false,stringTMap,false);// condition为false,不拼接此查询条件
//x是字段,y是对应的值,使用Lambda表达式进行条件的校验
BiPredicate bi = (x, y) -> x .equals("ID");
queryWrapper.allEq(bi,stringTMap);//WHERE ID = ?
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 值1 AND 值2
between(R column, Object val1, Object val2)
between(boolean condition, R column, Object val1, Object val2)
例: between("age", 18, 30)
--->age between 18 and 30
notBetween:NOT BETWEEN 值1 AND 值2
notBetween(R column, Object val1, Object val2)
notBetween(boolean condition, R column, Object val1, Object val2)
例: notBetween("age", 18, 30)
--->age not between 18 and 30
like:LIKE '%值%'
like(R column, Object val)
like(boolean condition, R column, Object val)
例: like("name", "王")
--->name like '%王%'
notLike:NOT LIKE '%值%'
notLike(R column, Object val)
notLike(boolean condition, R column, Object val)
例: notLike("name", "王")
--->name not like '%王%'
likeLeft:LIKE '%值'
likeLeft(R column, Object val)
likeLeft(boolean condition, R column, Object val)
例: likeLeft("name", "王")
--->name like '%王'
likeRight:LIKE '值%'
likeRight(R column, Object val)
likeRight(boolean condition, R column, Object val)
例: likeRight("name", "王")
--->name like '王%'
isNull:字段 IS NULL
isNull(R column)
isNull(boolean condition, R column)
例: isNull("name")
--->name is null
isNotNull: 字段 IS NULL
isNotNull(R column)
isNotNull(boolean condition, R column)
例: isNotNull("name")
--->name is not null
in:字段 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:字段 NOT IN
notIn(R column, Collection> value)
notIn(boolean condition, R column, Collection> value)
字段 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)
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:字段 NOT IN ( sql语句 )
notInSql(R column, String inValue)
notInSql(boolean condition, R column, String inValue)
例: 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")
--->age not in (select id from table where id < 3)
groupBy:分组:GROUP BY 字段, ...
groupBy(R... columns)
groupBy(boolean condition, R... columns)
例: groupBy("id", "name")
--->group by id,name
orderByAsc:排序:ORDER BY 字段, ... ASC
orderByAsc(R... columns)
orderByAsc(boolean condition, R... columns)
例: orderByAsc("id", "name")
--->order by id ASC,name ASC
orderByDesc 排序:ORDER BY 字段, ... DESC
orderByDesc(R... columns)
orderByDesc(boolean condition, R... columns)
例: orderByDesc("id", "name")
--->order by id DESC,name DESC
orderBy:排序:ORDER BY 字段, ...
orderBy(boolean condition, boolean isAsc, R... columns)
排序:ORDER BY 字段, ...例: orderBy(true, true, "id", "name")
--->order by id ASC,name ASC
queryWrapper.orderByAsc("aa_as");
queryWrapper.orderByDesc("ab_AAA");
//ORDER BY aa_as ASC , ab_AAA DESC
having:HAVING ( sql语句 )
having(String sqlHaving, Object... params)
having(boolean condition, String sqlHaving, Object... params)
例: having("sum(age) > 10")
--->having sum(age) > 10
例: having("sum(age) > {0}", 11)
--->having sum(age) > 11
or:拼接 OR
or()
or(boolean condition)
例:注意事项:
主动调用or
表示紧接着下一个方法不是用and
连接!(不调用or
则默认为使用and
连接)
eq("id",1).or().eq("name","老王")
--->id = 1 or name = '老王'
or(Function func)
or(boolean condition, Function func)
OR 嵌套例: or(i -> i.eq("name", "李白").ne("status", "活着"))
--->or (name = '李白' and status <> '活着')
queryWrapper.eq("ID" ,13 );
queryWrapper.or();
queryWrapper.eq("ID" ,14);
queryWrapper.ne("aa_as","rtget" );
//ID = ? OR (ID = ? AND aa_as <> ?)
queryWrapper.eq("ID" ,13 ).or(i->i.eq("ID" ,14 ).ne("aa_as","rtget" )).or(i->i.eq("aa_as","测试2" ))//要在一条上才能连上 or(Function func)
//WHERE ID = ? OR ( ID = ? AND aa_as <> ? ) OR ( aa_as = ? )
and:AND 嵌套
and(Function func)
and(boolean condition, Function func)
例: and(i -> i.eq("name", "李白").ne("status", "活着"))
--->and (name = '李白' and status <> '活着')
nested:正常嵌套 不带 AND 或者 OR
nested(Function func)
nested(boolean condition, Function func)
例: nested(i -> i.eq("name", "李白").ne("status", "活着"))
--->(name = '李白' and status <> '活着')
apply:拼接 sql
apply(String applySql, Object... params)
apply(boolean condition, String applySql, Object... params)
例:注意事项:
该方法可用于数据库函数
动态入参的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:无视优化规则直接拼接到 sql 的最后
last(String lastSql)
last(boolean condition, String lastSql)
例:注意事项:
只能调用一次,多次调用以最后一次为准
有sql注入的风险,请谨慎使用
last("limit 1")
exists:拼接 EXISTS ( sql语句 )
exists(String existsSql)
exists(boolean condition, String existsSql)
例: exists("select id from table where age = 1")
--->exists (select id from table where age = 1)
notExists:拼接 NOT EXISTS ( sql语句 )
notExists(String notExistsSql)
notExists(boolean condition, String notExistsSql)
例: notExists("select id from table where age = 1")
--->not exists (select id from table where age = 1)
QueryWrapper(select)
select:设置查询字段说明:
继承自 AbstractWrapper ,自身的内部属性 entity 也用于生成 where 条件
及 LambdaQueryWrapper, 可以通过 new QueryWrapper().lambda() 方法获取
select(String... sqlSelect)
select(Predicate predicate)
select(Class entityClass, Predicate predicate)
例:说明:
以上方分法为两类.
第二类方法为:过滤查询字段(主键除外),入参不包含 class 的调用前需要wrapper
内的entity
属性有值!
这两类方法重复调用以最后一次为准
select("id", "name", "age")
例: select(i -> i.getProperty().startsWith("test"))
excludeColumns:排除查询字段
UpdateWrapper(update)已从
3.0.5
版本上移除此方法!
set说明:
继承自AbstractWrapper
,自身的内部属性entity
也用于生成 where 条件
及LambdaUpdateWrapper
, 可以通过new UpdateWrapper().lambda()
方法获取!
set(String column, Object val)
set(boolean condition, String column, Object val)
SQL SET 字段例: set("name", "老李头")
例: set("name", "")
--->数据库字段值变为空字符串例: set("name", null)
--->数据库字段值变为null
setSql:设置 SET 部分 SQL
setSql(String sql)
例: set("name = '老李头')
lambda
获取 LambdaWrapper
在
QueryWrapper
中是获取LambdaQueryWrapper
在
UpdateWrapper
中是获取LambdaUpdateWrapper
使用 Wrapper 自定义SQL
Service.java需求来源:
在使用了mybatis-plus
之后, 自定义SQL的同时也想使用Wrapper
的便利应该怎么办?
在mybatis-plus
版本3.0.7
得到了完美解决
版本需要大于或等于3.0.7
, 以下两种方案取其一即可
mysqlMapper.getAll(Wrappers.lambdaQuery().eq(MysqlData::getGroup, 1));
方案一 注解方式 Mapper.java
@Select("select * from mysql_data ${ew.customSqlSegment}")
List getAll(@Param(Constants.WRAPPER) Wrapper wrapper);
方案二 XML形式 Mapper.xml
SELECT * FROM mysql_data ${ew.customSqlSegment}
分页查询
mybatis plus提供了分页功能,可以轻松实现分页;
//设置查询参数
Page page=new Page<>();
page.setCurrent(1);
page.setSize(2);
//开始查询
IPage page2 = aaaBbbCcDao.page(page);
/**
getCurrent():当前页数;
getPages():总页数;
getSize():查询数量;
getTotal():总数量;
getRecords():查询结果;
若是当前页>总页数,返回[];
若是当前页数<1,查询第一页数据;
*/
自定义SQL查询分页数据
将Page page
参数设置为查询的第一个参数,不需要拼接分页查询条件,mybatis plus会自动执行分页查询;例:
/**
*
* 查询 : 根据state状态查询用户列表,分页显示
* 注意!!: 如果入参是有多个,需要加注解指定参数名才能在xml中取值
*
*
* @param page 分页对象,xml中可以从里面进行取值,传递参数 Page 即自动分页,必须放在第一位(你可以继承Page实现自己的分页对象)
* @param state 状态
* @return 分页对象
*/
@Select("SELECT id,name FROM user WHERE state=#{state}")
IPage selectPageVo(Page page, @Param("state") Integer state);
热部署(已过时)
在3.1.0已经完全移除了....我们用的是3.1.1,用不了了o(╥﹏╥)o
逻辑删除(不建议使用)在正式项目中,删除数据时很多时候不是将数据直接删除,而是创建一个字段,用不同的数据表示不同的状态;
比如创建一个enable
字段,enable=1
,则表示数据使用中,enable=0
,则表示数据逻辑上已经删除了,平时使用时,这条数据默认不查询;
在mybatis plus中可以设置逻辑删除的查询;
mybatis-plus:
global-config:
db-config:
logic-delete-value: 0 # 逻辑已删除值(默认为 1)
logic-not-delete-value: 1 # 逻辑未删除值(默认为 0)
entity
//在代表删除的字段上添加注解:
@TableLogic
private Integer enable;
使用
//默认在查询的时候就会拼接上enable的条件
dao.list();//where enable=1
注意,此查询条件不会被覆盖,使用功能需谨慎
//若是想要查询已经删除的数据,将无法查询....
queryWrapper.eq("enable","0" );
dao.list(queryWrapper);//WHERE enable=1 AND enable = 0
所以还是自己写吧o(╥﹏╥)o
枚举配置 扫描通用枚举自3.1.0开始,可配置默认枚举处理类来省略扫描通用枚举配置,3.1.0之前和之后的配置是不同的,我们就不研究3.1.0之前的使用方法了(#^.^#)
mybatis-plus:
# 支持统配符 * 或者 ; 分割
typeEnumsPackage: com.baomidou.springboot.entity.enums,自定义枚举
entity配置/JSON序列化处理
Jackson
在需要响应描述字段的get方法上添加@JsonValue注解即可
Fastjson
全局处理方式```java
FastJsonConfig config = new FastJsonConfig();
//设置WriteEnumUsingToString
config.setSerializerFeatures(SerializerFeature.WriteEnumUsingToString);
converter.setFastJsonConfig(config);
- 局部处理方式
```java
@JSONField(serialzeFeatures= SerializerFeature.WriteEnumUsingToString)
private UserStatus status;
实现 IEnum 接口
例:年龄使用枚举
创建枚举
@AllArgsConstructor
public enum AgeEnum implements IEnum {
ONE(1, "一岁"),
TWO(2, "二岁"),
THREE(3, "三岁");
private int value;
private String desc;
@Override
public Integer getValue() {
return this.value;
}
public String geDesc() {
return this.desc;
}
}
entity中设置枚举
public class User{
/**
* 名字
* 数据库字段: name varchar(20)
*/
private String name;
/**
* 年龄,IEnum接口的枚举处理
* 数据库字段:age INT(3)
*/
private AgeEnum age;
}
使用
数据库中数据为":张三",3
json转换后为:"张三","THREE"
注意:age在set的时候需要设置枚举而不是之前的Integer了,但是用户可以自己设置set方法,将传入的Integer转为枚举再赋值....
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)