使用过MyBatis的同学应该都有过这种体会当类里面要添加或删减字段的时候,就要去修改Mapper.xml修改相对应的SQL语句,这样相对来说就有点麻烦容易出错。今天给大家介绍一个工资MyBatis-Plus,plus是加强的意思,那MyBatis-Plus就是MyBatis的加强版,MyBatis—plus就解决了刚刚上面所说的问题,当然他还有很多优点,今天就来学习一下SpringBoot如何整合MyBatis-Plus吧。
MyBatis-Plus的优点
1.无侵入,强大的CRUD功能;
2.支持lambda形式调用;
3.支持多种形式的自动生成主键;
4.内置代码生成器,内置分页插件;
5.内置全局拦截插件,内置sql注入剥离器;
对于 mybatis-plus 的使用,可以参照官网http://mp.baomidou.com/
一、创建数据库表
CREATE TABLE `tb_student` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`name` varchar(255) DEFAULT NULL,
`num` bigint(20) DEFAULT NULL,
`sex` varchar(255) DEFAULT NULL,
`age` int(11) DEFAULT NULL,
`native_place` varchar(255) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8mb4;
**二、创建SpringBoot项目
创建一个springboot项目 boketest
1、pom.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.2.5.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.zyyqc</groupId>
<artifactId>boketest</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>pom</packaging>
<name>boketest</name>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.46</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>
<exclusions>
<exclusion>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.1.10</version>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.1.0</version>
</dependency>
<!-- mybatis plus 代码生成器依赖 -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<version>3.1.0</version>
</dependency>
<!-- 代码生成器模板 -->
<dependency>
<groupId>org.freemarker</groupId>
<artifactId>freemarker</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
2.编写码生成器
CodeGenerator.Class
package com.zyyqc.boketest.generator;
import com.baomidou.mybatisplus.core.exceptions.MybatisPlusException;
import com.baomidou.mybatisplus.core.toolkit.StringPool;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.generator.AutoGenerator;
import com.baomidou.mybatisplus.generator.InjectionConfig;
import com.baomidou.mybatisplus.generator.config.*;
import com.baomidou.mybatisplus.generator.config.po.TableInfo;
import com.baomidou.mybatisplus.generator.config.rules.NamingStrategy;
import com.baomidou.mybatisplus.generator.engine.FreemarkerTemplateEngine;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class CodeGenerator {
/**
* <p>
* 读取控制台内容
* </p>
*/
public static String scanner(String tip) {
Scanner scanner = new Scanner(System.in);
StringBuilder help = new StringBuilder();
help.append("请输入" + tip + ":");
System.out.println(help.toString());
if (scanner.hasNext()) {
String ipt = scanner.next();
if (StringUtils.isNotEmpty(ipt)) {
return ipt;
}
}
throw new MybatisPlusException("请输入正确的" + tip + "!");
}
public static void main(String[] args) {
// 代码生成器
AutoGenerator mpg = new AutoGenerator();
// 全局配置
GlobalConfig gc = new GlobalConfig();
//获取项目当前所在文件夹位置
String projectPath = System.getProperty("user.dir");
gc.setOutputDir(projectPath + "/src/main/java");
gc.setAuthor("zhangxiansho");
gc.setOpen(false);
// service 命名方式
gc.setServiceName("%sService");
// service impl 命名方式
gc.setServiceImplName("%sServiceImpl");
// 自定义文件命名,注意 %s 会自动填充表实体属性!
gc.setMapperName("%sMapper");
gc.setXmlName("%sMapper");
gc.setFileOverride(true);
gc.setActiveRecord(true);
// XML 二级缓存
gc.setEnableCache(false);
// XML ResultMap
gc.setBaseResultMap(true);
// XML columList
gc.setBaseColumnList(false);
mpg.setGlobalConfig(gc);
// 数据源配置
DataSourceConfig dsc = new DataSourceConfig();
dsc.setUrl("jdbc:mysql://127.0.0.1:3306/boke?useUnicode=true&useSSL=false&characterEncoding=utf-8");
dsc.setDriverName("com.mysql.jdbc.Driver");
dsc.setUsername("root");
dsc.setPassword("root");
mpg.setDataSource(dsc);
// 包配置
PackageConfig pc = new PackageConfig();
pc.setParent("com.zyyqc.boketest");
pc.setEntity("entity");
pc.setService("service");
pc.setServiceImpl("service.impl");
mpg.setPackageInfo(pc);
// 自定义配置
InjectionConfig cfg = new InjectionConfig() {
@Override
public void initMap() {
// to do nothing
}
};
// 如果模板引擎是 freemarker
String templatePath = "/templates/mapper.xml.ftl";
// 如果模板引擎是 velocity
// String templatePath = "/templates/mapper.xml.vm";
// 自定义输出配置
List<FileOutConfig> focList = new ArrayList<>();
// 自定义配置会被优先输出
focList.add(new FileOutConfig(templatePath) {
@Override
public String outputFile(TableInfo tableInfo) {
// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!
return projectPath + "/src/main/resources/mapper/" + tableInfo.getEntityName() + "Mapper" + StringPool.DOT_XML;
}
});
cfg.setFileOutConfigList(focList);
mpg.setCfg(cfg);
// 配置模板
TemplateConfig templateConfig = new TemplateConfig();
// 配置自定义输出模板
//指定自定义模板路径,注意不要带上.ftl/.vm, 会根据使用的模板引擎自动识别
// templateConfig.setEntity("templates/entity2.java");
// templateConfig.setService();
// templateConfig.setController();
templateConfig.setXml(null);
mpg.setTemplate(templateConfig);
// 策略配置
StrategyConfig strategy = new StrategyConfig();
strategy.setNaming(NamingStrategy.underline_to_camel);
strategy.setColumnNaming(NamingStrategy.underline_to_camel);
//strategy.setSuperEntityClass("cn.com.bluemoon.demo.entity");
strategy.setEntityLombokModel(true);
strategy.setRestControllerStyle(true);
// 公共父类
//strategy.setSuperControllerClass("cn.com.bluemoon.demo.controller");
// 写于父类中的公共字段
//strategy.setSuperEntityColumns("id");
strategy.setInclude(scanner("表名,多个英文逗号分割").split(","));
strategy.setControllerMappingHyphenStyle(true);
//去掉数据库表名的前缀,这里我的数据库中的表名加了“tb_”前缀
strategy.setTablePrefix("tb_");
mpg.setStrategy(strategy);
mpg.setTemplateEngine(new FreemarkerTemplateEngine());
mpg.execute();
}
}
代码生成器中的一些基本配置比如作者名称,包的路径,数据库链接地址根据自己的实际情况进行调整。
3.执行代码生成器
执行代码生成器中的main方法,在控制台中输入要生成的表的表名,如下图

执行后可以清楚的看到自动创建了controller,entity,service,mapper等新包,并且生成了对应的java代码。

通过图片可以清楚的看出生成了tb_student和tb_excel_zip两张表对应的java类。
4.application.yml
spring:
#数据库配置
datasource:
url: jdbc:mysql://127.0.0.1:3306/boke?useUnicode=true&useSSL=false&characterEncoding=utf-8
username: root
password: root
# 使用druid数据源
type: com.alibaba.druid.pool.DruidDataSource
driver-class-name: com.mysql.jdbc.Driver
5.简单的CRUD
刚刚已经自动生成了大部分的java代码了,这样大大提高了我们的开发效率,不仅如此MyBatis-Plus还封装了大量的方法,下面就来试一下。
@RestController
@RequestMapping("/student")
public class StudentController {
@Resource
private StudentService studentService;
@PostMapping("/saveOrUpdate")
public String saveOrUpdate(@RequestBody Student student) {
boolean saveOrUpdate = true;
if (Objects.isNull(student.getId())) {
saveOrUpdate = studentService.save(student);
} else {
saveOrUpdate = studentService.updateById(student);
}
if (saveOrUpdate) {
return "保存成功!";
} else {
return "保存失败!";
}
}
@PostMapping("/delete")
public String delete(Long id) {
boolean b = studentService.removeById(id);
if (b) {
return "删除成功";
} else {
return "删除失败";
}
}
@PostMapping("/list")
public List<Student> list() {
List<Student> list = studentService.list();
return list;
}
}
上面所调用的save,updateById,removeById,list都是mybatis-plus封装好的使用很方便的,还有很多方法大家可以自己去研究一下。
6.分页查询
mybatis-plus内置了分页插件用起来也是很方便的首先需要添加一个配置类
@Configuration
public class MybatisPlusConfig {
@Bean
public PaginationInterceptor paginationInterceptor() {
PaginationInterceptor paginationInterceptor = new PaginationInterceptor();
return paginationInterceptor;
}
}
@PostMapping("/listBody")
public List<Student> list(@RequestBody StudentQuery query) {
Page<Student> page = studentService.queryPageList(query);
return page.getRecords();
}
@Builder
@Data
@AllArgsConstructor
@NoArgsConstructor
public class StudentQuery implements Serializable{
private static final long Serializable = 1L;
private int currentPage = 1;
private int pageSize = 10;
}
StudentQuery 类是分页查询的条件,里面包含了要查询的当前页currentPage和每一页的数据量pageSize,默认值是取第1页每一页10条数据。
接下来是service和mapper中的代码
@Service
public class StudentServiceImpl extends ServiceImpl<StudentMapper, Student> implements StudentService {
@Resource
private StudentMapper studentMapper;
@Override
public Page<Student> queryPageList(StudentQuery query) {
Page<Student> page = new Page<>(query.getCurrentPage(), query.getPageSize());
LambdaQueryWrapper<Student> queryWrapper = new LambdaQueryWrapper<>();
List<Student> students = studentMapper.queryPageList(page,queryWrapper);
page.setRecords(students);
return page;
}
/**
* <p>
* Mapper 接口
* </p>
*
* @author zhangxiansho
* @since 2020-04-01
*/
public interface StudentMapper extends BaseMapper<Student> {
List<Student> queryPageList(Page<Student> page, @Param("queryWrapper") Wrapper<Student> queryWrapper);
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.zyyqc.boketest.mapper.StudentMapper">
<!-- 通用查询映射结果 -->
<resultMap id="BaseResultMap" type="com.zyyqc.boketest.entity.Student">
<id column="id" property="id" />
<result column="name" property="name" />
<result column="num" property="num" />
<result column="sex" property="sex" />
<result column="age" property="age" />
<result column="native_place" property="nativePlace" />
</resultMap>
<select id="queryPageList" resultType="com.zyyqc.boketest.entity.Student">
select * from tb_student
<where>
${queryWrapper.sqlSegment}
</where>
</mapper>
接下来做个单元测试看一下结果
@Test
void queryPageList() {
Page<Student> page = studentService.queryPageList(new StudentQuery());
if (CollectionUtils.isNotEmpty(page.getRecords())) {
page.getRecords().forEach(System.out::println);
}
}
![image.png]
由图可知已经查出了第一页的10条数据。
好了到现在MyBatis-Plus的基本增删改查,分页操作就完成了,MyBatis-plus的更多使用就待你自己慢慢深入发掘了。
