Mybatis-plus 1. 什么是MyBatis-Plus MyBatis-Plus 是一个 Mybatis 增强版工具,在 MyBatis 上扩充了其他功能没有改变其基本功能,为了简化开发提交效率而存在。
官网文档地址: https://mp.baomidou.com/guide/
2. springboot中快速使用Mybatis-plus 使用插件 使用 IDEA 安装一个 mybatis-plus 插件
增加依赖 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-boot-starter</artifactId> <version>3.4.1</version> </dependency> <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.1.4</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>6.0.6</version> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid</artifactId> <version>1.1.24</version> </dependency>
配置application.yml 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 server: port: 8080 spring: datasource: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://localhost:3306/java160?serverTimezone=Asia/Shanghai&useSSL=false username: root password: root type: com.alibaba.druid.pool.DruidDataSource initialSize: 5 minIdle: 5 maxActive: 20 maxWait: 60000 mybatis: type-aliases-package: com.hyy.entity
增加Config类 1 2 3 4 5 6 7 8 @Configuration public class MyConfig { @Bean("dataSource") @ConfigurationProperties(prefix = "spring.datasource") public DataSource druid () { return new DruidDataSource (); } }
增加实体类 1 2 3 4 5 6 7 8 9 10 @Data public class Teacher { String tno; String tname; String tsex; @DateTimeFormat(pattern = "yyyy-MM-dd") Date tbirthday; String prof; String depart; }
编写Mapper类 1 2 public interface TeacherMapper extends BaseMapper <Teacher> {}
修改启动类 增加@MapperScan注解
1 2 3 4 5 6 7 8 9 @SpringBootApplication @MapperScan(basePackages = "com.hyy.dao") public class Base04MybatisplusApplication { public static void main (String[] args) { SpringApplication.run(Base04MybatisplusApplication.class, args); } }
编写测试控制器 此控制器跳开service,直接调用了Mapper
1 2 3 4 5 6 7 8 9 @RestController public class TeacherController { @Autowired TeacherMapper teacherMapper; @RequestMapping("/getall") public List<Teacher> selectAll () { return teacherMapper.selectList(null ); } }
配置日志 1 2 3 mybatis-plus: configuration: log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
常用注解 @TableName:用于表名,放在entity上面,value值是数据库表名(主要用于pojo和数据库表名不一致的情况下)
@TableId:用于定义表的主键,其value是表的主键column名,type是指主键类型
@TableField:用于定义表的非主键字段。
value:指定数据库表中的cloumn名
exist:用于表明当前的field是否是数据库表的一个属性,会影响sql语句
fill:用于指定数据的自动填充策略,一般用于修改时间或者创建时间,默认不填充
@TableLogic:用于定义表的逻辑删除字段。
value:用于定义未删除状态的值
delval:用于定义删除状态的值
代码生成器 新版(3.5.1之后) 依赖 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 <dependency > <groupId > org.springframework.boot</groupId > <artifactId > spring-boot-starter-web</artifactId > </dependency > <dependency > <groupId > com.baomidou</groupId > <artifactId > mybatis-plus-boot-starter</artifactId > <version > 3.5.3</version > </dependency > <dependency > <groupId > com.baomidou</groupId > <artifactId > mybatis-plus-generator</artifactId > <version > 3.5.3</version > </dependency > <dependency > <groupId > org.apache.velocity</groupId > <artifactId > velocity-engine-core</artifactId > <version > 2.3</version > </dependency >
配置 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 @Test void mybatisGenerator () { String url = "jdbc:mysql://localhost:3306/authc?serverTimezone=UTC&useSSL=false" ; FastAutoGenerator fastAutoGenerator = FastAutoGenerator.create(url, "root" , "root" ) .globalConfig(builder -> { builder.author("mamp" ) .fileOverride() .outputDir("D://" ); }); fastAutoGenerator.packageConfig(builder -> { builder.parent("net" ) .moduleName("system" ) .controller("controller" ) .service("service" ) .entity("domain" ) .mapper("mapper" ) .serviceImpl("impl" ); }); fastAutoGenerator.strategyConfig(builder -> { builder.entityBuilder() .naming(NamingStrategy.underline_to_camel) .columnNaming(NamingStrategy.underline_to_camel); builder.controllerBuilder().enableRestStyle(); }); fastAutoGenerator.execute(); }
模板 定义模板 定义模板并放在resources/templates目录下,以下为controller.java.vm
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 package ${package.Controller}; import org.springframework.web.bind.annotation.RequestMapping; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import ${package.Entity}.${entity}; import ${package.Service}.${table.serviceName}; import org.springframework.web.bind.annotation.DeleteMapping; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RestController; import javax.annotation.Resource; import java.util.List; #if(${restControllerStyle}) import org.springframework.web.bind.annotation.RestController; #else import org.springframework.stereotype.Controller; #end #if(${superControllerClassPackage}) import ${superControllerClassPackage}; #end /** * <p> * $!{table.comment} 前端控制器 * </p> * * @author ${author} * @since ${date} */ #if(${restControllerStyle}) @RestController #else @Controller #end @RequestMapping("#if(${package.ModuleName})/${package.ModuleName}#end/#if(${controllerMappingHyphenStyle})${controllerMappingHyphen}#else${table.entityPath}#end") #if(${kotlin}) class ${table.controllerName}#if(${superControllerClass}) : ${superControllerClass}()#end #else #if(${superControllerClass}) public class ${table.controllerName} extends ${superControllerClass} { #else public class ${table.controllerName} { } #end @Resource ${table.serviceName} #serviceName(); @GetMapping("list") public List<${entity}> doList(){ QueryWrapper<${entity}> query = new QueryWrapper<>(); query.likeLeft("phone","23") .like("email","2189"); List<${entity}> list = #serviceName().list(query); return list; } @GetMapping("findOne/{id}") public ${entity} findOne(@PathVariable("id") Long id){ return #serviceName().getById(id); } @DeleteMapping("delete/{id}") public void deleteOne(@PathVariable("id") Long id){ ${table.serviceName.substring(0,1).toLowerCase()}${table.serviceName.substring(1)}.removeById(id); } } #end #macro(serviceName) ${table.serviceName.substring(0,1).toLowerCase()}${table.serviceName.substring(1)} #end
修改生成代码 1 2 3 4 5 6 7 8 9 10 @Test void mybatisGenerator () { ... String controllerTemplate="templates/controller.java" ; fastAutoGenerator.templateConfig(builder -> { builder.controller(controllerTemplate); }); fastAutoGenerator.execute(); }
旧版(3.4.x) 使用代码生成器能够方便的生成所需要的代码
注意在主类中需要增加@EnableAutoConfiguration或者给@SpringBootApplication注解添加属性exclude = {DataSourceAutoConfiguration.class}
1 2 3 4 5 6 @SpringBootApplication(exclude = {DataSourceAutoConfiguration.class}) public class GeneratorApplication { public static void main (String[] args) { SpringApplication.run(GeneratorApplication.class, args); } }
增加依赖 1 2 3 4 5 6 7 8 9 10 11 <dependency > <groupId > com.baomidou</groupId > <artifactId > mybatis-plus-generator</artifactId > <version > 3.4.1</version > </dependency > <dependency > <groupId > org.apache.velocity</groupId > <artifactId > velocity-engine-core</artifactId > <version > 2.3</version > </dependency >
创建代码生成器 1 AutoGenerator mpg = new AutoGenerator ();
全局配置 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 GlobalConfig gc = new GlobalConfig ();String projectPath = "D:\\springbootProject\\springbootsample\\base05-mybatisplus-generator" ;gc.setOutputDir(projectPath + "/src/main/java" ); gc.setAuthor("mamp" ); gc.setOpen(false ); gc.setFileOverride(false ); gc.setIdType(IdType.ASSIGN_ID); gc.setDateType(DateType.ONLY_DATE); gc.setServiceName("%sService" ); mpg.setGlobalConfig(gc);
设置数据源 1 2 3 4 5 6 7 8 9 10 11 12 13 14 DataSourceConfig dsc = new DataSourceConfig ();String url="jdbc:mysql://localhost:3306/java160?" +"serverTimezone=Asia/Shanghai&useSSL=false" ; System.out.println(url); dsc.setUrl(url); dsc.setDriverName("com.mysql.cj.jdbc.Driver" ); dsc.setUsername("root" ); dsc.setPassword("root" ); mpg.setDataSource(dsc);
设置包 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 PackageConfig pc = new PackageConfig ();pc.setParent("com.hyy" ); pc.setModuleName("system" ); pc.setEntity("entity" ); pc.setMapper("mapper" ); pc.setService("service" ); pc.setController("controller" ); mpg.setPackageInfo(pc);
设置生成策略 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 StrategyConfig strategy = new StrategyConfig ();strategy.setInclude("teacher" ); strategy.setNaming(NamingStrategy.underline_to_camel); strategy.setColumnNaming(NamingStrategy.underline_to_camel); strategy.setEntityLombokModel(true ); strategy.setRestControllerStyle(true ); strategy.setControllerMappingHyphenStyle(true ); mpg.setStrategy(strategy);
执行代码生成操作
其他功能 自动填充数据 给POJO的属性@TableField上增加fill属性
定义一个实现MetaObjectHandler 接口的组件(需要能够扫描到)
逻辑删除 支持的数据类型为Integer,Boolean以及Date类型。
操作方法:给实体类的对象增加@TableLogic(value=”0”,delval = “1”)注解
value:正常有效数据值
delval:删除时的值
使用 mybatis-plus 封装好的方法时,会自动添加逻辑删除的功能。若是自定义的 sql 语句,需要手动添加逻辑。
全局设置(3.5.1以后版本) 在application.yml文件中增加以下配置,并在entity的指定属性上增加@TableLogic注解
1 2 3 4 5 6 7 mybatis-plus global-config: db-config: logic-delete-field: del_flag # 全局逻辑删除的实体字段名 logic-delete-value: 1 # 逻辑已删除值(默认为 1 ) logic-not-delete-value: 0 # 逻辑未删除值(默认为 0 )
entity
1 2 3 4 5 6 7 8 @Data @TableName(value="sample") public class Sample implements Serializable { ... @TableLogic private Integer delFlag; }
单个设置 使用@TableLogic的value和delValue来设置
1 2 3 4 5 6 7 8 9 10 11 12 13 14 @Data @EqualsAndHashCode(callSuper = false) public class Teacher implements Serializable { private static final long serialVersionUID = 1L ; 。。。 @TableLogic(value="0",delval = "1") @TableField("deleteFlag") private Integer deleteflag; }
分页插件 注入mybatisplus分页插件 1 2 3 4 5 6 7 8 9 @Configuration public class MybatisPlusConfig { @Bean public MybatisPlusInterceptor mybatisPlusInterceptor() { MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor(); interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL)); return interceptor; } }
使用mybatis提供的方法 mybatis提供了一系列分页的方法,例如page
1 2 3 4 5 6 7 8 @GetMapping("page") public Page<Sample> findPage () { Page<Sample> page = new Page <>(); page.setCurrent(1 ); page.setSize(2 ); Page<Sample> page1 = sampleService.page(page); return page1; }
使用自定义方法
修改mapper
1 2 3 4 5 6 7 8 9 10 11 12 13 @Mapper public interface SampleMapper extends BaseMapper <Sample> { IPage<Sample> selectPageVo (IPage<?> page, Sample sample) ; } <select id="selectPageVo" resultType="net.wanho.base01.entity.Sample" > select * from sample where name like concat ('%' ,#{sample.name},'%' ) </select>
修改service
1 2 3 4 5 6 7 8 9 10 11 12 13 14 public interface ISampleService extends IService <Sample> { IPage<Sample> selectPageVo (IPage<?> page, Sample sample) ; } @Service public class SampleServiceImpl extends ServiceImpl <SampleMapper, Sample> implements ISampleService { @Override public IPage<Sample> selectPageVo (IPage<?> page, Sample sample) { SampleMapper baseMapper = this .getBaseMapper(); return baseMapper.selectPageVo(page,sample); } }
测试处理器
1 2 3 4 5 6 7 8 9 10 11 @GetMapping("mypage") public Page<Sample> findMyPage(){ Page<Sample> page = new Page<>(); page.setCurrent(1); page.setSize(2); Sample sample = new Sample(); sample.setName("test"); IPage<Sample> page1 = sampleService.selectPageVo(page,sample); return (Page<Sample>)page1; }
乐观锁(3.5.1) 条件构造器 QueryWrapper:查询条件构造器
1 2 3 4 5 6 7 8 QueryWrapper<Teacher> queryWrapper = new QueryWrapper <>(); queryWrapper .select("tno" , "tname" , "tbirthday" ) .eq("tno" , '702' ) .like("tname" , "j" ); teacherService .list(queryWrapper) .forEach(System.out::println);