1、导入mybatisplus依赖
创建代码生成器模块 并在pom中导入下面依赖
<!-- mybatis-plus依赖 -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.3.1</version>
</dependency>
<!--代码生成模式插件 3.0.3以后需要手动设置依赖-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-generator</artifactId>
<version>3.3.1.tmp</version>
</dependency>
<!-- 模板引擎 依赖,MyBatis-Plus 支持 Velocity-->
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity-engine-core</artifactId>
<version>2.1</version>
</dependency>
<!--数据库连接依赖-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.18</version>
</dependency>
2、准备好模板
将控制层和实体类的模版拷贝到上面创建的代码生成模块resources /templates目录下,可以自定义需要导入的包,下面的模版中就引入了swagger接口文档和validation校验
如果不使用模版mybatisplus就会使用自带的默认模版
package ${package.Controller};
import ${package.Service}.${table.serviceName};
import ${package.Entity}.${entity};
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import javax.validation.Valid;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
@Tag(name = "$!{table.comment}",description = "$!{table.comment}")
@RestController
@RequestMapping("/${table.entityPath}")
public class ${entity}Controller{
@Autowired
public ${table.serviceName} ${table.entityPath}Service;
@Operation( summary= "保存${entity}",description = "基础对象保存接口")
@Parameter(name = "${table.entityPath}",description = "保存的对象",required = true)
@PostMapping
public JSONResult save(@RequestBody @Valid ${entity} ${table.entityPath}){
return JSONResult.success(${table.entityPath}Service.save(${table.entityPath}));
}
@Operation( summary= "修改${entity}",description = "基础对象修改接口")
@Parameter(name = "${table.entityPath}",description = "修改的对象",required = true)
@PutMapping
public JSONResult update(@RequestBody @Valid ${entity} ${table.entityPath}){
return JSONResult.success(${table.entityPath}Service.updateById(${table.entityPath}));
}
//删除对象
@Operation( summary= "删除${entity}",description = "基础对象删除接口,采用状态删除")
@Parameter(name = "id",description = "删除的对象ID",required = true)
@DeleteMapping(value="/{id}")
public JSONResult delete(@PathVariable("id") Long id){
return JSONResult.success(${table.entityPath}Service.removeById(id));
}
//获取对象
@Operation( summary= "获取${entity}",description = "基础对象获取接口")
@Parameter(name = "id",description = "查询的对象ID",required = true)
@GetMapping(value = "/{id}")
public JSONResult get(@PathVariable("id")Long id){
return JSONResult.success(${table.entityPath}Service.getById(id));
}
//获取列表:PageQueryWrapper作为通用的查询对象
@Operation( summary= "查询${entity}列表",description = "基础对象列表查询,不带分页")
@Parameter(name = "query",description = "查询条件",required = true)
@PostMapping(value = "/list")
public JSONResult list(@RequestBody PageQueryWrapper<${entity}> query){
QueryWrapper<${entity}> wrapper = new QueryWrapper<>();
//实体类作为查询条件
wrapper.setEntity(query.getQuery());
return JSONResult.success(${table.entityPath}Service.list(wrapper));
}
//分页查询
@Operation( summary= "查询${entity}分页列表",description = "基础对象列表查询,带分页")
@Parameter(name = "query",description = "查询条件,需要指定分页条件",required = true)
@PostMapping(value = "/pagelist")
public JSONResult page(@RequestBody PageQueryWrapper<${entity}> query){
//分页查询
Page<${entity}> page = new Page<${entity}>(query.getPage(),query.getRows());
QueryWrapper<${entity}> wrapper = new QueryWrapper<>();
//实体类作为查询条件
wrapper.setEntity(query.getQuery());
//分页查询
page = ${table.entityPath}Service.page(page,wrapper);
//返回结果
return JSONResult.success(new PageResult<${entity}>(page.getTotal(),page.getRecords()));
}
}
设置好实体类模版要导入的lombok和swagger以及JsonFormat时间格式化
package ${package.Entity};
#foreach($pkg in ${table.importPackages})
import ${pkg};
#end
#if(${swagger2})
import io.swagger.v3.oas.annotations.media.Schema;
#end
#if(${entityLombokModel})
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.experimental.Accessors;
import com.fasterxml.jackson.annotation.JsonFormat;
#end
/**
* <p>
* $!{table.comment}
* </p>
*
* @author ${author}
* @since ${date}
*/
#if(${entityLombokModel})
@Data
#if(${superEntityClass})
@EqualsAndHashCode(callSuper = true)
#else
@EqualsAndHashCode(callSuper = false)
#end
@Accessors(chain = true)
#end
#if(${table.convert})
@TableName("${table.name}")
#end
#if(${swagger2})
@Schema(name = "${entity}对象", description = "$!{table.comment}")
#end
#if(${superEntityClass})
public class ${entity} extends ${superEntityClass}#if(${activeRecord})<${entity}>#end {
#elseif(${activeRecord})
public class ${entity} extends Model<${entity}> {
#else
public class ${entity} implements Serializable {
#end
#if(${entitySerialVersionUID})
private static final long serialVersionUID=1L;
#end
## ---------- BEGIN 字段循环遍历 ----------
#foreach($field in ${table.fields})
#if(${field.keyFlag})
#set($keyPropertyName=${field.propertyName})
#end
#if(${swagger2})
@Schema(name = "${field.propertyName}", description = "${field.comment}")
#else
#if("$!field.comment" != "")
/**
* ${field.comment}
*/
#end
#end
#if(${field.keyFlag})
## 主键
@JsonFormat(shape = JsonFormat.Shape.STRING)
#if(${field.keyIdentityFlag})
@TableId(value = "${field.name}", type = IdType.AUTO)
#elseif(!$null.isNull(${idType}) && "$!idType" != "")
@TableId(value = "${field.name}", type = IdType.${idType})
#elseif(${field.convert})
@TableId("${field.name}")
#end
## 普通字段
#elseif(${field.fill})
## ----- 存在字段填充设置 -----
#if(${field.convert})
@TableField(value = "${field.name}", fill = FieldFill.${field.fill})
#else
@TableField(fill = FieldFill.${field.fill})
#end
#elseif(${field.convert})
@TableField("${field.name}")
#end
#if(${versionFieldName}==${field.name})
@Version
#end
#if(${logicDeleteFieldName}==${field.name})
@TableLogic
#end
private ${field.propertyType} ${field.propertyName};
#end
## ---------- END 字段循环遍历 ----------
#if(!${entityLombokModel})
#foreach($field in ${table.fields})
#if(${field.propertyType.equals("boolean")})
#set($getprefix="is")
#else
#set($getprefix="get")
#end
public ${field.propertyType} ${getprefix}${field.capitalName}() {
return ${field.propertyName};
}
#if(${entityBuilderModel})
public ${entity} set${field.capitalName}(${field.propertyType} ${field.propertyName}) {
#else
public void set${field.capitalName}(${field.propertyType} ${field.propertyName}) {
#end
this.${field.propertyName} = ${field.propertyName};
#if(${entityBuilderModel})
return this;
#end
}
#end
## --foreach end---
#end
## --end of #if(!${entityLombokModel})--
#if(${entityColumnConstant})
#foreach($field in ${table.fields})
public static final String ${field.name.toUpperCase()} = "${field.name}";
#end
#end
#if(${activeRecord})
@Override
protected Serializable pkVal() {
#if(${keyPropertyName})
return this.${keyPropertyName};
#else
return null;
#end
}
#end
#if(!${entityLombokModel})
@Override
public String toString() {
return "${entity}{" +
#foreach($field in ${table.fields})
#if($!{foreach.index}==0)
"${field.propertyName}=" + ${field.propertyName} +
#else
", ${field.propertyName}=" + ${field.propertyName} +
#end
#end
"}";
}
#end
}
3、代码生成配置文件
在代码生成模块的resources包下创建一个config-driver.properties文件
OutputDir= E:/software/code/项目名//服务模块src/main/java // 写代码要生成的包路径
OutputDirXml=E:/software/code/项目名/服务模块/src/main/resources // mapper.xml文件输出位置
author= 作者名字
parent= 项目包域名
jdbc.driver=com.mysql.cj.jdbc.Driver // 连接mysql的连接池
jdbc.url=jdbc:mysql://127.0.0.1:3306/数据库名?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false
jdbc.user=root
jdbc.pwd=123456
4、构建代码生成器
使用下面代码来配置代码生成器
public static void main(String[] args) {
//读取配置文件,改为要读取的配置文件,注意不要加properties后缀
ResourceBundle rb = ResourceBundle.getBundle("config-driver");
//业务代码输出路径
String outputDir = rb.getString("OutputDir");
//sql映射文件输出路径
String outputDirXml = rb.getString("OutputDirXml");
//作者
String author = rb.getString("author");
// 代码生成器
AutoGenerator mpg = new AutoGenerator();
// 全局配置
GlobalConfig gc = new GlobalConfig();
// 代码输出位置
gc.setOutputDir(outputDir);
// 作者
gc.setAuthor(author);
// 打开代码生成目录
gc.setOpen(false);
//生成 resultMap
gc.setBaseResultMap(true);
//生成查询列明
gc.setBaseColumnList(true);
//日期类型
gc.setDateType(DateType.ONLY_DATE);
//ID使用雪花算法
gc.setIdType(IdType.ASSIGN_ID);
//添加接口文档注解
gc.setSwagger2(true);
mpg.setGlobalConfig(gc);
// 数据源配置
DataSourceConfig dsc = new DataSourceConfig();
// 数据库类型
dsc.setDbType(DbType.MYSQL);
dsc.setTypeConvert(new MySqlTypeConvert());
// 连接属性
dsc.setDriverName(rb.getString("jdbc.driver"));
dsc.setUsername(rb.getString("jdbc.user"));
dsc.setPassword(rb.getString("jdbc.pwd"));
dsc.setUrl(rb.getString("jdbc.url"));
mpg.setDataSource(dsc);
// 表策略配置
StrategyConfig strategy = new StrategyConfig();
strategy.setTablePrefix(new String[] { "t_" });// 此处可以修改为您的表前缀
strategy.setNaming(NamingStrategy.underline_to_camel);// 表名生成策略
strategy.setInclude(new String[]{
"t_driver",
}); // 需要生成的表
//使用lombok
strategy.setEntityLombokModel(true);
strategy.setEntitySerialVersionUID(true);
//乐观锁字段
strategy.setVersionFieldName("version");
//逻辑删除字段
strategy.setLogicDeleteFieldName("deleted");
//domain的父类
//strategy.setSuperEntityClass("org.zy.pojo.BaseDomain");
//controller的父类
//strategy.setSuperControllerClass("org.zy.controller.BaseController");
//生成注解
strategy.setEntityTableFieldAnnotationEnable(true);
strategy.setEntitySerialVersionUID(true);
mpg.setStrategy(strategy);
// 包配置
PackageConfig pc = new PackageConfig();
//基础路径 cn.xxx
pc.setParent(rb.getString("parent"));
//controller的包
pc.setController("controller.manager");
pc.setService("service");
pc.setServiceImpl("service.impl");
pc.setEntity("pojo.domain");
pc.setMapper("mapper");
mpg.setPackageInfo(pc);
// 注入自定义配置,可以在 VM 中使用 cfg.abc 【可无】
InjectionConfig cfg = new InjectionConfig() {
@Override
public void initMap() {
this.setMap(new HashMap<String, Object>());
}
};
//文件生成配置
List<FileOutConfig> focList = new ArrayList<FileOutConfig>();
//controller的输出配置
focList.add(new FileOutConfig("/templates/controller.java.vm") {
@Override
public String outputFile(TableInfo tableInfo) {
//合并好的内容输出到哪儿?
return outputDir+ "/org/zy/controller/manager/" + tableInfo.getEntityName() + "Controller.java";
}
});
// 调整 domain 生成目录演示
focList.add(new FileOutConfig("/templates/entity.java.vm") {
@Override
public String outputFile(TableInfo tableInfo) {
return outputDir+ "/org/zy/pojo/domain/" + tableInfo.getEntityName() + ".java";
}
});
// 调整 xml 生成目录演示
focList.add(new FileOutConfig("/templates/mapper.xml.vm") {
@Override
public String outputFile(TableInfo tableInfo) {
return outputDirXml+ "/org/zy/mapper/" + tableInfo.getEntityName() + "Mapper.xml";
}
});
cfg.setFileOutConfigList(focList);
mpg.setCfg(cfg);
// 自定义模板配置,可以 copy 源码 mybatis-plus/src/main/resources/templates 下面内容修改,
// 放置自己项目的 src/main/resources/templates 目录下, 默认名称可以不配置,也可以自定义模板名称
TemplateConfig tc = new TemplateConfig();
tc.setService("/templates/service.java.vm");
tc.setServiceImpl("/templates/serviceImpl.java.vm");
tc.setMapper("/templates/mapper.java.vm");
tc.setEntity(null);
tc.setController(null);
tc.setXml(null);
// 如上任何一个模块如果设置 空 OR Null 将不生成该模块。
mpg.setTemplate(tc);
// 执行生成
mpg.execute();
}
5、服务整合mybatisPlus
第一步:在要生成代码的服务pom中导入如下依赖
<!--mybatisplus持久层依赖-->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.3.1</version>
</dependency>
<!-- mysql驱动-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.33</version>
</dependency><!--mysql依赖-->
<!--连接池依赖-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.1.23</version>
</dependency>
第二步:在服务的resource加入mybatisPlus的yaml配置(可以直接配置在nacos中公共配置中,每个服务的数据库url可单独配置)
server:
port: 10020
spring:
application:
name: @artifactId@
# mybaits-plus数据源配置
datasource:
username: root
password: 123456
url: jdbc:mysql://127.0.0.1:3306/数据库名?serverTimezone=Asia/Shanghai&characterEncoding=utf8
driver-class-name: com.mysql.cj.jdbc.Driver
type: com.alibaba.druid.pool.DruidDataSource # 配置阿里的连接池
druid: # Druid 【监控】相关的全局配置
# 配置初始化大小、最小、最大
initial-size: 5
minIdle: 10
max-active: 20
# 配置获取连接等待超时的时间(单位:毫秒)
max-wait: 60000
########### 启用内置过滤器(第一个 stat必须,否则监控不到SQL)##########
filters: stat,wall,log4j2
web-stat-filter:
enabled: true
stat-view-servlet:
enabled: true
allow: # 设置白名单,不填则允许所有访问
url-pattern: /druid/*
login-username: admin # 控制台管理用户名和密码
login-password: 123456
filter:
stat:
enabled: true
log-slow-sql: true # 慢 SQL 记录
slow-sql-millis: 2000
merge-sql: true
wall:
config:
multi-statement-allow: true
# mybatis-plus配置
mybatis-plus:
type-aliases-package: 域名.domain,域名.query #别名包扫描
mapper-locations: classpath:域名文件夹/mapper/*Mapper.xml #SQL映射文件扫描
global-config:
db-config: #设置逻辑删除,通过把delete字段改成0而不是直接删除数据
logic-not-delete-value: 0
logic-delete-value: 1
configuration:
map-underscore-to-camel-case: true # 开启驼峰命名转换法
cache-enabled: false #禁用缓存
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl # 配置日志,在控制台输出SQL
第三步:在服务中创建config编写mybatisPlus的配置类
@Configuration
//扫描Mybatis的mapper映射器
@MapperScan("mapper包路径")
public class MybatisPlusConfig {
//分页插件配置对象,Mybatis-plus需要此配置对象
@Bean
public PaginationInterceptor paginationInterceptor() {
return new PaginationInterceptor();
}
//乐观锁插件
@Bean
public OptimisticLockerInterceptor optimisticLockerInterceptor(){
return new OptimisticLockerInterceptor();
}
}
6、生成服务基础代码
以上步骤都完成之后,运行代码生成器的main方法,就能生成代码