在spring framework
所支持的orm
框架中,mybatis
相比 hibernate
,spring
自己提供的支持是相对少的,这在开发过程当中对使用mybatis
进行开发的程序员来讲无疑产生不少难处。java
为此,开源上也产生了不少三方对mybatis
的一些加强工具,好比ourbatis
、mybatis-generator
等等。这篇咱们主要来讲下功能丰富、如今还在迭代的一款国人开发的加强工具mybatis-plus
。就像官方文档说的那样mysql
咱们的愿景是成为 MyBatis 最好的搭档,就像 魂斗罗 中的 1P、2P,基友搭配,效率翻倍。git
能够看出,mybatis-plus
是了为了提升效率和简化配置而生的。下面就来展现下在springboot
下如何整合mybatis-plus
程序员
首先是建立一个springboot
工程github
引入相关依赖(springboot
相关、mybaits
、mybatis-plus
等等)web
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!-- springboot对mybaits的自动配置依赖 -->
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>1.3.2</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- mybatis-plus相关依赖 -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.0.5</version>
</dependency>
</dependencies>
复制代码
使用mybaits-plus
的代码生成器映射生成代码,咱们这里所使用的数据库为mysql
。这个在另一篇文章上说明,这里就不讲述了。spring
在这里,mybaits-plus
提供了BaseMapper
、BaseService
这些基类来提供一些操做的支持,好比sql
save(T t)
saveOrUpdate(T t)
update(T t, Wrapper<T> wrapper)
page(IPage<T> page, Wrapper<T> queryWrapper)
等等。数据库
下面,咱们就简单介绍下springboot
中怎么运用mybaits-plus
小程序
首先是说到配置,这里默认以yml
文件来进行对mybaits-plus
的配置。
mybatis-plus:
#MyBatis Mapper 所对应的 XML 文件位置
mapper-locations: classpath*:mapper/*.xml
# MyBaits 别名包扫描路径,经过该属性能够给包中的类注册别名,
#注册后在 Mapper 对应的 XML 文件中能够直接使用类名,而不用使用全限定的类名(即 XML 中调用的时候不用包含包名)
typeAliasesPackage: com.luwei.models
# 与 typeAliasesPackage 一块儿使用,仅扫描以该类做为父类的类
# type-aliases-super-type: java.lang.Object
# 配置扫描通用枚举,配置该属性,会对枚举类进行注入
typeEnumsPackage: com.luwei.demo.mybatisplusdemo.envm
# 该包下的类注册为自定义类型转换处理类,用于属性类型转换
# type-handlers-package: com.luwei.demo.mybatisplusdemo.handler
# 指定 mybatis 处理器
# executorType: simple
configuration:
#使用驼峰法映射属性,配置这个resultType能够映射
map-underscore-to-camel-case: true
global-config:
db-config:
# 配置代表前缀,例如表设计时表名为tb_manager,对应entity为Manager
table-prefix: tb_
#逻辑已删除值
logic-delete-value: 1
#逻辑未删除值
logic-not-delete-value: 0
# 是否开启like查询,即对 stirng 字段是否使用 like,默认不开启
# column-like: false
logging:
level:
# 日志级别,显示操做sql
com.luwei.demo.mybatisplusdemo.mapper: debug
复制代码
基本上这些配置都能知足通常的应用了。
上面说到,BaseMapper
和BaseService
已经实现了一些基本操做,下面简单说下这些接口的用法
查询中Mybatis-plus
提供多种封装好的方式,包括对主键查询、指定条件查询、分页查询等。
Manager manager1 = managerService.getById(1);
Assert.assertNotNull(manager1);
LambdaQueryWrapper<Manager> wrapper = new LambdaQueryWrapper<Manager>().like(Manager::getName, "na");
List<Manager> managerList = managerService.list(wrapper);
Assert.assertFalse(managerList.isEmpty());
//先配置page分页插件配置
Page page = new Page<>(1, 2);
IPage<Manager> managerPage = managerService.page(page, wrapper);
Assert.assertFalse(managerPage.getRecords().isEmpty());
//获取map对象
Map<String, Object> map = managerService.getMap(wrapper);
System.out.println(map);
Object obj = managerService.getObj(wrapper);
System.out.println(obj);
try {
//如有多个结果,抛出异常
managerService.getOne(wrapper, true);
}catch (RuntimeException e) {
e.printStackTrace();
System.out.println("异常捕获");
}
复制代码
save(T t)
方法,实际就是将对象持久化到数据库中,这里会产生一条insert语句,并执行。
@Transactional
public void add() {
Manager manager = new Manager();
manager.setAccount("account");
manager.setRole(RoleEnum.ROOT);
manager.setPassword("password");
manager.setName("name");
save(manager);
}
复制代码
日志输出:
==> Preparing: INSERT INTO tb_manager ( account, name, password, role ) VALUES ( ?, ?, ?, ? )
==> Parameters: account(String), name(String), password(String), 0(Integer)
<== Updates: 1
复制代码
提供的update
、updateOrSave
、upateById
均可以实现数据更新。 各自的区别在于
update
:根据条件筛选并更新指定字段updateOrSave
:对对象进行更新,对未存储的对象进行插入updateById
:根据id对对象进行更新@Transactional
public void updateManager() {
Manager manager = getById(1);
manager.setName("testUpdate");
updateById(manager);
//saveOrUpdate(manager);
//update(new Manager(), new UpdateWrapper<Manager>().lambda().set(Manager::getName, "test").eq(Manager::getManagerId, 1));
}
复制代码
在删除中,除了通常的物理删除外,mybaits-plus
还提供了逻辑删除的支持。
若是须要使用逻辑删除,除了上述配置外,还须要添加一个配置bean来装配插件。
@Bean
public ISqlInjector sqlInjector() {
return new LogicSqlInjector();
}
复制代码
这样在使用删除时,会对记录中标记为删除标识的字段进行更改,在查询和更新时,也只是针对删除标识为未删除的记录。
public void deleteManager() {
LambdaQueryWrapper<Manager> wrapper = new LambdaQueryWrapper<Manager>().eq(Manager::getManagerId, 4);
System.out.println(baseMapper.delete(wrapper));
/*Map<String, Object> deleteMap = new HashMap<>(); //使用表字段名 deleteMap.put("manager_id", 4); baseMapper.deleteByMap(deleteMap);*/
/*baseMapper.deleteById(4);*/
//属于service下的方法
/*LambdaQueryWrapper<Manager> wrapper = new LambdaQueryWrapper<Manager>().eq(Manager::getManagerId, 4); remove(wrapper);*/
}
复制代码
在查询、更新、删除这些操做中,咱们每每须要定义条件或者设置属性,也就是where
子句和set
语句,若是不是直接经过sql去处理,在mybatis-plus
中,也提供了一种包装器来实现。
AbstractWrapper
囊括了几乎知足平常须要的条件操做,和jpa
的specification
同样,它支持动态产生条件,也支持使用lambda
表达式去组装条件。他是QueryWrapper
和UpdateWrapper
的父类
一些经常使用的wrapper
方法
Map<String, Object> conditionMap = new HashMap<>();
//使用表字段名
conditionMap.put("name", "name");
conditionMap.put("manager_id", 1);
//allEq(BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull)
//filter:忽略字段
//null2IsNull:为true则在map的value为null时调用 isNull 方法,为false时则忽略value为null的
QueryWrapper<Manager> queryWrapper = new QueryWrapper<Manager>().allEq((r, v) -> r.indexOf("name") > 0, conditionMap, true);
managerService.list(queryWrapper);
复制代码
//like(R column, Object val) -> column like '%na%'
//likeLeft -> column like '%na'
//likeRight -> column like 'na%'
//and(Function<This, This> func) -> and (column = val)
LambdaQueryWrapper<Manager> lambdaWrapper = new LambdaQueryWrapper<Manager>().like(Manager::getName, "na").and((r) -> r.eq(Manager::getDisabled, false));
managerService.list(lambdaWrapper);
复制代码
//orderBy(boolean condition, boolean isAsc, R... columns) -> order by columns isAsc
LambdaQueryWrapper<Manager> lambdaWrapper = new LambdaQueryWrapper<Manager>().orderBy(true, false, Manager::getManagerId);
managerService.list(lambdaWrapper);
复制代码
//select 用于挑选属性
LambdaQueryWrapper<Manager> lambdaWrapper = new LambdaQueryWrapper<Manager>().select(Manager::getName, Manager::getDisabled);
managerService.list(lambdaWrapper);
复制代码
//set(R column, Object val) -> update T set colunm = val
managerService.update(new Manager(), new UpdateWrapper<Manager>().lambda().set(Manager::getName, "newName").eq(Manager::getManagerId, 4));
复制代码
诸如还有其余像eq
,lte
,isNull
,orderBy
,or
,exists
等限定方法,这里就不一一介绍了。
引入分页,除了配置上,还须要添加插件bean
@Bean
public PaginationInterceptor paginationInterceptor() {
return new PaginationInterceptor();
}
复制代码
在使用时,自定义查询中,参数中添加Page
对象,并要求放在参数中的第一位
IPage<ManagerPageVO> selectManagerPage(Page page, @Param("roleEnum")RoleEnum roleEnum, @Param("managerId") Integer managerId, @Param("name") String name);
复制代码
<select id="selectManagerPage" resultType="com.luwei.pojos.manager.ManagerPageVO">
<![CDATA[
select manager_id, account, name, role, disabled, create_time, last_login_time from tb_manager where role = #{roleEnum} and deleted = false
]]>
<if test="name != null">
<![CDATA[
and (name like CONCAT('%',#{name},'%') or account like CONCAT('%',#{name},'%'))
]]>
</if>
<if test="managerId != null">
<![CDATA[
and manager_id = #{managerId}
]]>
</if>
</select>
<select id="selectForSpecialCondition" resultType="com.luwei.entity.Manager">
select
<include refid="Base_Column_List" />
from tb_manager
where name like '%admin%'
</select>
复制代码
在mybaits-plus
中,有多种主键生成策略,它们分别是
因为咱们公司使用的是mysql
自己的自增策略,因此选择使用 IdType.AUTO。
@ApiModelProperty(value = "管理员id")
@TableId(value = "manager_id", type = IdType.AUTO)
private Integer managerId;
复制代码
至于 ID_WORKER 和 UUID 的不一样,在于它们的惟一键生成策略不一样,ID_WORKER 按照官方的介绍,是使用Sequence
做为基础产生惟一键。
为了让mybaits
更好地使用枚举,mybatis-plus
提供了枚举扫描注入
具体配置,首先是配置扫描路径
# 配置扫描通用枚举,配置该属性,会对枚举类进行注入
typeEnumsPackage: com.luwei.demo.mybatisplusdemo.envm
复制代码
在枚举类中实现接口,用于获取具体值
//实现此接口用于获取值
public interface BaseEnum<E extends Enum<?>, T> {
T getValue();
String getDisplayName();
}
复制代码
这样,基本上就能够在mybatis
上使用枚举类型了。
上面描述了mybitis-plus
基本用法,其实除了以上,它还提供了不少方便的插件和应用,包括xml热加载、乐观锁插件、性能分析插件等,这些因为篇幅和主题的缘由我就不在这里阐述了。但愿这篇能够带你很快地上手这个当前热门的mybaits
加强工具,提升开发效率。
![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
---|---|---|---|---|---|---|---|---|
掘金 | segmentfault | V2EX | 知乎 | 博客园 | 开源中国 | github | 简书 | 芦苇科技 |
广州芦苇科技Java开发团队
芦苇科技-广州专业软件外包服务公司
提供微信小程序、APP应用研发、UI设计等专业服务,专一于互联网产品咨询、品牌设计、技术研发等领域
访问 www.talkmoney.cn 了解更多
万能说明书 | 早起日记Lite | 凹凸壁纸 | 言财