MyBatis Plus Generator代码生成

一、MyBatis Plus Generator

MyBatis Plus是一个功能强大的持久层框架,它简化了MyBatis的使用,提供了许多便捷的功能。其中,MyBatis Plus Generator是一个强大的代码生成器,可以帮助我们快速地根据数据库表结构生成对应的实体类、映射文件和DAO接口。在MyBatis Plus Generator中,我们可以使用模板ftl文件来自定义生成的代码样式。本文将介绍如何使用MyBatis Plus Generator通过模板ftl文件生成代码。

二、使用介绍

2.1 引入依赖
   <!--mybatis-plus--><dependency><groupId>com.baomidou</groupId><artifactId>mybatis-plus-boot-starter</artifactId><version>3.4.1</version></dependency><dependency><groupId>com.baomidou</groupId><artifactId>mybatis-plus-annotation</artifactId><version>3.4.1</version></dependency><dependency><groupId>com.baomidou</groupId><artifactId>mybatis-plus-generator</artifactId><version>3.4.1</version></dependency><dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId></dependency><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></dependency><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger2</artifactId><version>2.9.2</version><exclusions><exclusion><groupId>io.swagger</groupId><artifactId>swagger-annotations</artifactId></exclusion><exclusion><groupId>io.swagger</groupId><artifactId>swagger-models</artifactId></exclusion></exclusions></dependency><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger-ui</artifactId><version>2.9.2</version></dependency><dependency><groupId>io.swagger</groupId><artifactId>swagger-annotations</artifactId><version>1.5.21</version></dependency><dependency><groupId>io.swagger</groupId><artifactId>swagger-models</artifactId><version>1.5.21</version></dependency>
2.2 模版文件

在这里插入图片描述

在项目的resources文件夹下创建一个名为templates的文件夹,用于存放模板ftl文件。

2.2.1 controller.java.ftl
package ${package.Controller};import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
<#if restControllerStyle>
import org.springframework.web.bind.annotation.RestController;
<#else>
import org.springframework.stereotype.Controller;
</#if>
<#if swagger2>
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
</#if>
<#if superControllerClassPackage??>
import ${superControllerClassPackage};
</#if>
import ${package.Service}.${table.serviceName};/*** @author ${author}* @description ${table.comment!}前端控制器* @date ${date}*/
<#if swagger2>
@Api(tags = "${table.comment!}前端控制器")
</#if>
<#if restControllerStyle>
@RestController
<#else>
@Controller
</#if>
@RequestMapping("<#if package.ModuleName?? && package.ModuleName != "">/${package.ModuleName}</#if>/<#if controllerMappingHyphenStyle??>${controllerMappingHyphen}<#else>${table.entityPath}</#if>")
<#if kotlin>
class ${table.controllerName}<#if superControllerClass??> : ${superControllerClass}()</#if>
<#else>
<#if superControllerClass??>
public class ${table.controllerName} extends ${superControllerClass} {
<#else>
public class ${table.controllerName} {
</#if>@Resourceprivate ${table.serviceName} ${table.entityPath}Service;@ApiOperation(value = "按id查询")@GetMapping("/single")public ResultBean<${entity}VO> queryById(Long id) {return ResultBean.success(${table.entityPath}Service.queryById(id));}@ApiOperation(value = "按id删除")@PostMapping("/delete/single")public ResultBean deleteById(Long id) {${table.entityPath}Service.deleteById(id);return ResultBean.success();}@ApiOperation(value = "按id更新")@PostMapping("/update/single")public ResultBean<${entity}VO> update(@RequestBody ${entity}VO vo) {vo = ${table.entityPath}Service.update(vo);return ResultBean.success(vo);}@ApiOperation(value = "新增")@PostMapping("/insert/single")public ResultBean<${entity}VO> insert(@RequestBody ${entity}VO vo) {vo = ${table.entityPath}Service.insert(vo);return ResultBean.success(vo);}}
</#if>
2.2.2 dto.java.ftl
package ${cfg.packageParent}.DTO;<#list table.importPackages as pkg><#if !(pkg?contains('mybatis') || pkg?contains('entity'))><#if pkg == 'java.time.LocalDateTime'>import java.util.Date;<#else >import ${pkg};</#if></#if>
</#list>
import java.io.Serializable;
<#if swagger2>import io.swagger.annotations.ApiModel;import io.swagger.annotations.ApiModelProperty;
</#if><#if entityLombokModel>import lombok.Data;import lombok.EqualsAndHashCode;<#if chainModel>import lombok.experimental.Accessors;</#if>
</#if>/*** @author ${author}* @description ${table.comment!}VO* @date ${date}*/
<#if entityLombokModel>
@Data
<#--@EqualsAndHashCode(callSuper = false)-->
<#--@Accessors(chain = true)-->
</#if>
<#if swagger2>
@ApiModel(value = "${entity}DTO对象", description = "${table.comment!} DTO")
</#if>
public class ${entity}DTO implements Serializable {private static final long serialVersionUID = 1L;
<#list table.fields as field><#if field.comment!?length gt 0><#if swagger2>/*** ${field.comment}*/@ApiModelProperty(value = "${field.comment}")<#else>/*** ${field.comment}*/</#if></#if><#if field.propertyType == 'LocalDateTime'>@DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")private LocalDateTime ${field.propertyName};<#else>private ${field.propertyType} ${field.propertyName};</#if>
</#list>
<#------------  END 字段循环遍历  ---------->
<#if !entityLombokModel><#list table.fields as field><#if field.propertyType == "boolean"><#assign getprefix="is"/><#else><#assign getprefix="get"/></#if><#if field.propertyType == "LocalDateTime"><#assign betterPropertyType="Date"/><#else><#assign betterPropertyType="${field.propertyType}"/></#if>public ${betterPropertyType} ${getprefix}${field.capitalName}() {return ${field.propertyName};}<#if chainModel>public ${entity} set${field.capitalName}(${betterPropertyType} ${field.propertyName}) {<#else>public void set${field.capitalName}(${betterPropertyType} ${field.propertyName}) {</#if>this.${field.propertyName} = ${field.propertyName};<#if chainModel>return this;</#if>}</#list>
</#if>
<#if !entityLombokModel>@Overridepublic String toString() {return "${entity}{" +<#list table.commonFields as field><#if field_index==0>"${field.propertyName}=" + ${field.propertyName} +<#else>", ${field.propertyName}=" + ${field.propertyName} +</#if></#list><#list table.fields as field><#if field_index==0>"${field.propertyName}=" + ${field.propertyName} +<#else>", ${field.propertyName}=" + ${field.propertyName} +</#if></#list>"}";}
</#if>
}
2.2.3 entity.java.ftl
package ${package.Entity};<#list table.importPackages as pkg>
<#if pkg == 'java.time.LocalDateTime'>
import java.util.Date;
<#else >
import ${pkg};
</#if>
</#list>
<#if swagger2>
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
</#if>
<#if entityLombokModel>
import lombok.Data;
import lombok.EqualsAndHashCode;<#if chainModel>
import lombok.experimental.Accessors;</#if>
</#if>/**
* @author ${author}
* @description ${table.comment!}实体
* @date ${date}
*/
<#if entityLombokModel>
@Data<#if superEntityClass??>
@EqualsAndHashCode(callSuper = true)<#else>
@EqualsAndHashCode(callSuper = false)</#if>
<#--    <#if chainModel>-->
<#--@Accessors(chain = true)-->
<#--    </#if>-->
</#if>
<#if table.convert>
@TableName("${table.name}")
</#if>
<#if swagger2>
@ApiModel(value="${entity}对象", description="${table.comment!}")
</#if>
<#if superEntityClass??>
public class ${entity} extends ${superEntityClass}<#if activeRecord><${entity}></#if> {
<#elseif activeRecord>
public class ${entity} extends Model<${entity}> {
<#else>
public class ${entity} implements Serializable {
</#if><#if entitySerialVersionUID>private static final long serialVersionUID = 1L;
</#if>
<#-- ----------  BEGIN 字段循环遍历  ---------->
<#list table.fields as field><#if field.keyFlag><#assign keyPropertyName="${field.propertyName}"/></#if><#if field.comment!?length gt 0><#if swagger2>/*** ${field.comment}*/@ApiModelProperty(value = "${field.comment}")<#else>/*** ${field.comment}*/</#if></#if><#if field.keyFlag>
<#--         主键 --><#if field.keyIdentityFlag>@TableId(value = "${field.annotationColumnName}", type = IdType.AUTO)<#elseif idType??>@TableId(value = "${field.annotationColumnName}", type = IdType.${idType})<#elseif field.convert>@TableId("${field.annotationColumnName}")</#if><#-- 普通字段 --><#elseif field.fill??><#-- -----   存在字段填充设置   -----><#if field.convert>@TableField(value = "${field.annotationColumnName}", fill = FieldFill.${field.fill})<#else>@TableField(fill = FieldFill.${field.fill})</#if><#elseif field.convert>@TableField("${field.annotationColumnName}")</#if><#-- 乐观锁注解 --><#if (versionFieldName!"") == field.name>@Version</#if><#-- 逻辑删除注解 --><#if (logicDeleteFieldName!"") == field.name>@TableLogic</#if><#if field.propertyType == 'LocalDateTime'>private Date ${field.propertyName};<#else>private ${field.propertyType} ${field.propertyName};</#if>
</#list>
<#------------  END 字段循环遍历  ---------->
<#if !entityLombokModel><#list table.fields as field><#if field.propertyType == "boolean"><#assign getprefix="is"/><#else><#assign getprefix="get"/></#if><#if field.propertyType == "LocalDateTime"><#assign betterPropertyType="Date"/><#else><#assign betterPropertyType="${field.propertyType}"/></#if>public ${betterPropertyType} ${getprefix}${field.capitalName}() {return ${field.propertyName};}<#if chainModel>public ${entity} set${field.capitalName}(${betterPropertyType} ${field.propertyName}) {<#else>public void set${field.capitalName}(${betterPropertyType} ${field.propertyName}) {</#if>this.${field.propertyName} = ${field.propertyName};<#if chainModel>return this;</#if>}</#list>
</#if><#if entityColumnConstant><#list table.fields as field>public static final String ${field.name?upper_case} = "${field.name}";</#list>
</#if>
<#if activeRecord>@Overrideprotected Serializable pkVal() {<#if keyPropertyName??>return this.${keyPropertyName};<#else>return null;</#if>}</#if>
<#if !entityLombokModel>@Overridepublic String toString() {return "${entity}{" +<#list table.fields as field><#if field_index==0>"${field.propertyName}=" + ${field.propertyName} +<#else>", ${field.propertyName}=" + ${field.propertyName} +</#if></#list>"}";}
</#if>
}
2.2.4 mapper.java.ftl
package ${package.Mapper};<#--import ${package.Entity}.${entity};-->
import ${superMapperClassPackage};
<#--import ${cfg.packageParent}.vo.${entity}VO;-->
import java.util.List;import javax.validation.constraints.NotNull;/*** @author ${author}* @description ${table.comment!} Mapper 接口* @date ${date}*/
<#if kotlin>
interface ${table.mapperName} : ${superMapperClass}<${entity}>
<#else>
public interface ${table.mapperName} extends ${superMapperClass}<${entity}> {List<${entity}> queryByCondition(@NotNull ${entity}VO condition);
}
</#if>
2.2.5 mapper.xml.ftl
<?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="${package.Mapper}.mybatis.mapper.${table.mapperName}"><#if enableCache><!-- 开启二级缓存 --><cache type="org.mybatis.caches.ehcache.LoggingEhcache"/></#if><#if baseResultMap><!-- 通用查询映射结果 --><resultMap id="BaseResultMap" type="${package.Entity}.mybatis.entity.${entity}"><#list table.fields as field><#if field.keyFlag><#--生成主键排在第一位--><id column="${field.name}" property="${field.propertyName}"/></#if></#list><#list table.commonFields as field><#--生成公共字段 --><result column="${field.name}" property="${field.propertyName}"/></#list><#list table.fields as field><#if !field.keyFlag><#--生成普通字段 --><result column="${field.name}" property="${field.propertyName}"/></#if></#list></resultMap></#if><#if baseColumnList><!-- 通用查询结果列 --><sql id="Base_Column_List"><#list table.commonFields as field>${field.columnName},</#list>${table.fieldNames}</sql></#if><select id="queryByCondition" resultMap="BaseResultMap" parameterType="${cfg.packageParent}.dto.${entity}VO">SELECT<include refid="Base_Column_List"/>FROM ${table.name}<where><#list table.commonFields as field><#--生成公共字段 --><#if field.propertyType == 'String'><if test="${field.propertyName} != null and ${field.propertyName} != ''"><#else><if test="${field.propertyName} != null"></#if><#if field.propertyType == 'String'>AND ${field.annotationColumnName} LIKE CONCAT('%', ${"#{"}${field.propertyName}${"}"}, '%')<#else>AND ${field.annotationColumnName} = ${"#{"}${field.propertyName}${"}"}</#if></if></#list><#list table.fields as field><#if field.propertyType == 'String'><if test="${field.propertyName} != null and ${field.propertyName} != ''"><#else><#if field.propertyType == 'String'><if test="${field.propertyName} != null and ${field.propertyName} != ''"><#else><if test="${field.propertyName} != null"></#if></#if><#if field.propertyType == 'String'>AND ${field.annotationColumnName} LIKE CONCAT('%', ${"#{"}${field.propertyName}${"}"}, '%')<#else>AND ${field.annotationColumnName} = ${"#{"}${field.propertyName}${"}"}</#if></if></#list></where></select>
</mapper>
2.2.6 service.java.ftl
package ${package.Service};import ${superServiceClassPackage};/*** @author ${author}* @description ${table.comment!}服务类* @date ${date}*/
<#if kotlin>interface ${table.serviceName} : ${superServiceClass}<${entity}>
<#else>
public interface ${table.serviceName}  {${entity}DTO queryById(Long id);${entity}DTO update(${entity}DTO dto);${entity}DTO insert(${entity}DTO dto);void deleteById(Long id);}
</#if>
2.2.7 serviceImpl.java.ftl
package ${package.ServiceImpl};import java.util.List;
import java.util.ArrayList;
import javax.validation.constraints.NotNull;import ${package.Service}.${table.serviceName};
import ${superServiceImplClassPackage};import org.springframework.stereotype.Service;
import org.springframework.beans.BeanUtils;
import javax.annotation.Resource;/*** @author ${author}* @description ${table.comment!} 服务实现类* @date ${date}*/
@Service
<#if kotlin>
open class ${table.serviceImplName} : ${superServiceImplClass}<${table.mapperName}, ${entity}>(), ${table.serviceName} {}
<#else>
public class ${table.serviceImplName} extends ServiceImpl<${table.mapperName}, ${entity}> implements ${table.serviceName} {@Resourceprivate ${table.mapperName} ${table.entityPath}Mapper;private List<${entity}DTO> toDTOList(@NotNull List<${entity}> entities) {List<${entity}DTO> dtoList = new ArrayList<>(entities.size());for (${entity} entity : entities) {dtoList.add(toDTO(entity));}return dtoList;}private ${entity}DTO toDTO(@NotNull ${entity} entity) {${entity}DTO dto = new ${entity}DTO();BeanUtils.copyProperties(entity, dto);return dto;}@Overridepublic ${entity}DTO queryById(@NotNull Long id) {${entity} entity = ${table.entityPath}Mapper.selectById(id);return toDTO(entity);}@Overridepublic ${entity}DTO update(@NotNull ${entity}DTO dto) {${entity} entity = ${table.entityPath}Mapper.selectById(dto.getId());if (entity == null) {// 不存在return null;}BeanUtils.copyProperties(dto, entity, "id");${table.entityPath}Mapper.updateById(entity);return dto;}@Overridepublic ${entity}DTO insert(@NotNull ${entity}DTO dto) {${entity} entity = new ${entity}();BeanUtils.copyProperties(dto, entity, "id");${table.entityPath}Mapper.insert(entity);return toDTO(entity);}@Overridepublic void deleteById(@NotNull Long id) {${table.entityPath}Mapper.deleteById(id);}
}
</#if>
2.3 Swagger配置类
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;/*** @author Jerryean* @description swagger配置类* @date 2024/3/13**/
@Configuration
@EnableSwagger2
public class SwaggerConfig {@Beanpublic Docket docket() {return new Docket(DocumentationType.SWAGGER_2).enable(true).apiInfo(apiInfo()).groupName("默认")
//                .pathMapping("/test/api/web").select().apis(RequestHandlerSelectors.basePackage("com.test.web.controller")).paths(PathSelectors.any()).build();}private ApiInfo apiInfo() {return new ApiInfoBuilder().title("接口文档").description("接口文档").version("1.0").build();}
}
2.4 Generator逻辑

在这里插入图片描述

import cn.hutool.core.io.FileUtil;
import com.baomidou.mybatisplus.annotation.DbType;
import com.baomidou.mybatisplus.core.toolkit.StringPool;
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 lombok.extern.slf4j.Slf4j;import java.awt.*;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;/*** @author Jerryean* @date 2023/6/14*/
@Slf4j
public class CodeGenerator {static String entityDir;static String voDir;static String mapperDir;static String mapperXmlDir;static String serviceDir;static String controllerDir;static String serviceImplDir;// 生成路径static final String PRO_PATH = "D:\\companyCode\\";static final String CODE_PATH = "D:\\companyCode\\code\\";static final String XML_PATH = "D:\\companyCode\\mapper\\";static final String OPEN_DIR = "D:\\companyCode\\";// 是否覆盖static final boolean override = true;// 父类包static final String parentPkg = "com.cisdi";static final String author = "Jerryean";// 模板路径static final String templatePath = "/templates";// 生成的表static final String[] dataTables = {"student", "teacher"};private static class DataBaseConfig {static final String url = "jdbc:mysql://127.0.0.1:3306/test?useUnicode=true&useSSL=false&characterEncoding=utf8&serverTimezone=UTC";static final String username = "root";static final String password = "pwd123456";}public static void main(String[] args) {// 代码生成器AutoGenerator autoGenerator = new AutoGenerator();// 初始化输出文件夹init();// 删除之前生成的数据if (override) {delDir();}// 全局配置configGlobal(autoGenerator);// pkg设置configPkg(autoGenerator);// 数据源配置DataSourceConfig dsc = new DataSourceConfig();dsc.setDbType(DbType.MYSQL);dsc.setUrl(DataBaseConfig.url);dsc.setSchemaName("public");dsc.setDriverName("com.mysql.cj.jdbc.Driver");dsc.setUsername(DataBaseConfig.username);dsc.setPassword(DataBaseConfig.password);autoGenerator.setDataSource(dsc);// 配置指定自定义模板参数和类型InjectionConfig cfg = new InjectionConfig() {@Overridepublic void initMap() {Map<String, Object> map = new HashMap<>();map.put("baseResultMap", true);map.put("packageParent", parentPkg);this.setMap(map);}};List<FileOutConfig> focList = new ArrayList<>();importTemplate(focList);cfg.setFileOutConfigList(focList);autoGenerator.setCfg(cfg);// 配置策略StrategyConfig strategyConfig = new StrategyConfig();strategyConfig.setEntityLombokModel(true);// 包含的表strategyConfig.setInclude(dataTables);strategyConfig.setNaming(NamingStrategy.underline_to_camel);strategyConfig.setColumnNaming(NamingStrategy.underline_to_camel);strategyConfig.setRestControllerStyle(true);autoGenerator.setStrategy(strategyConfig);// 配置模板configTemplate(autoGenerator);// 执行autoGenerator.execute();//执行完之后打开try {// 要打开的文件夹路径File folder = new File(OPEN_DIR);// 打开文件夹Desktop.getDesktop().open(folder);} catch (IOException ignored) {}}static void init() {entityDir = CodeGenerator.CODE_PATH + "/entity";voDir = CodeGenerator.CODE_PATH + "/dto";mapperDir = CodeGenerator.CODE_PATH + "/mapper";mapperXmlDir = CodeGenerator.XML_PATH;serviceDir = CodeGenerator.CODE_PATH + "/service";serviceImplDir = CodeGenerator.CODE_PATH + "/service/impl";controllerDir = CodeGenerator.CODE_PATH + "/controller";}static void delDir() {List<String> dirs = new ArrayList<>();dirs.add(entityDir);dirs.add(voDir);dirs.add(mapperDir);dirs.add(mapperXmlDir);dirs.add(serviceDir);dirs.add(serviceImplDir);dirs.add(controllerDir);for (String per : dirs) {if (FileUtil.exist(per)) {FileUtil.del(per);} else {log.warn("no dir{}", per);}}}static void importTemplate(List<FileOutConfig> focList) {String entityTemplatePath = CodeGenerator.templatePath + "/entity.java.ftl";String mapperTemplatePath = CodeGenerator.templatePath + "/mapper.java.ftl";String mapperXmlTemplatePath = CodeGenerator.templatePath + "/mapper.xml.ftl";String voTemplatePath = CodeGenerator.templatePath + "/dto.java.ftl";String controllerTemplatePath = CodeGenerator.templatePath + "/controller.java.ftl";String serviceTemplatePath = CodeGenerator.templatePath + "/service.java.ftl";String serviceImplTemplatePath = CodeGenerator.templatePath + "/serviceImpl.java.ftl";// 自定义输出配置// 自定义配置会被优先输出focList.add(new FileOutConfig(entityTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return entityDir+ "/" + tableInfo.getEntityName() + ".java";}});focList.add(new FileOutConfig(mapperTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return mapperDir+ "/" + tableInfo.getEntityName() + "Mapper.java";}});focList.add(new FileOutConfig(mapperXmlTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return mapperXmlDir+ "/" + tableInfo.getEntityName() + "Mapper" + StringPool.DOT_XML;}});focList.add(new FileOutConfig(voTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return voDir+ "/" + tableInfo.getEntityName() + "DTO.java";}});focList.add(new FileOutConfig(controllerTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return controllerDir+ "/" + tableInfo.getEntityName() + "Controller.java";}});focList.add(new FileOutConfig(serviceTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return serviceDir+ "/" + tableInfo.getEntityName() + "Service.java";}});focList.add(new FileOutConfig(serviceImplTemplatePath) {@Overridepublic String outputFile(TableInfo tableInfo) {// 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!!return serviceImplDir+ "/" + tableInfo.getEntityName() + "ServiceImpl.java";}});}private static void configGlobal(AutoGenerator autoGenerator) {// 全局配置GlobalConfig gc = new GlobalConfig();gc.setOutputDir(CodeGenerator.PRO_PATH + "/src/main/java");gc.setAuthor(CodeGenerator.author);gc.setOpen(false);gc.setSwagger2(true);gc.setBaseResultMap(true);gc.setBaseColumnList(true);gc.setServiceName("%s" + ConstVal.SERVICE);autoGenerator.setGlobalConfig(gc);}private static void configPkg(AutoGenerator autoGenerator) {PackageConfig packageConfig = new PackageConfig();packageConfig.setParent(parentPkg);packageConfig.setController("controller");packageConfig.setService("service");packageConfig.setServiceImpl("service.impl");packageConfig.setMapper("mapper");packageConfig.setEntity("entity");autoGenerator.setPackageInfo(packageConfig);}private static void configTemplate(AutoGenerator autoGenerator) {TemplateConfig templateConfig = new TemplateConfig();// 只使用前面的自定义生成模板templateConfig.setController("");templateConfig.setService("");templateConfig.setServiceImpl("");templateConfig.setEntity("");templateConfig.setMapper("");templateConfig.setXml(null);autoGenerator.setTemplate(templateConfig);autoGenerator.setTemplateEngine(new FreemarkerTemplateEngine());}}

三、总结

MyBatis-Plus使用FTL模板能高效自动生成规范易读的代码,支持灵活定制和多平台,降低维护成本,提高开发效率。以上生成代码所用的逻辑,欢迎大家可以取下来使用。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/854854.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Java基础-案例练习-全是干货

目录 案例&#xff1a;卖飞机票 案例&#xff1a;找质数&#xff1a; 案例&#xff1a;开发验证码 案例&#xff1a;评委打分 案例&#xff1a;卖飞机票 package anlixunlian;import java.util.Scanner;/*机票价格按照淡季旺季、头等舱和经济舱收费、 输入机票原价、月份和…

使用Ollama+OpenWebUI本地部署阿里通义千问Qwen2 AI大模型

&#x1f3e1;作者主页&#xff1a;点击&#xff01; &#x1f916;AI大模型部署与应用专栏&#xff1a;点击&#xff01; &#x1f916;Ollama部署LLM专栏&#xff1a;点击&#xff01; ⏰️创作时间&#xff1a;2024年6月17日22点50分 &#x1f004;️文章质量&#xff…

探索设计模式——单例模式详解

前言&#xff1a;设计模式的作用主要是为了——利用设计方式的重用来自动地提高代码的重新利用、提高代码的灵活性、节省时间&#xff0c; 提高开发效率、低耦合&#xff0c;封装特性显著&#xff0c; 接口预留有利于扩展。 设计模式的种类有很多种&#xff0c;本篇内容主要讲解…

计算机网络5:运输层

概述 进程间基于网络的通信 计算机网络中实际进行通信的真正实体&#xff0c;是位于通信两端主机中的进程。 如何为运行在不同主机上的应用进程提供直接的逻辑通信服务&#xff0c;就是运输层的主要任务。运输层协议又称为端到端协议。 运输层向应用层实体屏蔽了下面网络核心…

【机器学习】机器学习重要分支——集成学习:理论、算法与实践

文章目录 引言第一章 集成学习的基本概念1.1 什么是集成学习1.2 集成学习的类型1.3 集成学习的优势 第二章 集成学习的核心算法2.1 Bagging方法2.2 Boosting方法2.3 Stacking方法 第三章 集成学习的应用实例3.1 图像分类3.2 文本分类 第四章 集成学习的未来发展与挑战4.1 模型多…

【前端项目笔记】2 主页布局

主页布局 element-ui提供的组件名称就是它的类名 ☆☆ CSS选择器&#xff1a; &#xff08;1&#xff09;基本选择器 类型选择器 p/span/div…… 类选择器 (.classname) ID选择器 (#idname) 通配选择器 ( * ) &#xff08;2&#xff09;属性选择器 选择具有特定属性或属性值的…

【C语言】解决C语言报错:Uninitialized Variable

文章目录 简介什么是Uninitialized VariableUninitialized Variable的常见原因如何检测和调试Uninitialized Variable解决Uninitialized Variable的最佳实践详细实例解析示例1&#xff1a;局部变量未初始化示例2&#xff1a;数组未初始化示例3&#xff1a;指针未初始化示例4&am…

C的I/O操作

目录 引言 一、文件与目录操作 1. 打开与关闭文件 2. 文件读写操作 3. 文件定位与错误处理 二、字符流与字节流 1. 字符流处理 2. 字节流处理 三、序列化与反序列化 1. 序列化 2. 反序列化 四、新的I/O&#xff08;NIO&#xff09; 表格总结 文件与目录操作 字符…

Java基础学习-数组

目录 数组定义 注意点&#xff1a; 地址值是数组在内存中实际存储的地址。 案例遍历&#xff1a;遍历数组得到每一个元素&#xff0c;求数组里面所有数据和 案例&#xff1a;定义数组&#xff0c;遍历能被3整除的数字 案例&#xff1a;遍历一个数组&#xff0c;奇数将当前…

守护电力心脏:国网电力监控运维平台的智慧使命

国网电力监控运维平台&#xff0c;以其强大的数据分析和处理能力&#xff0c;实现了对电网运行的实时监控。无论是电压波动、电流异常&#xff0c;还是设备故障&#xff0c;平台都能迅速捕捉并发出预警&#xff0c;确保电力供应的稳定和安全。 山海鲸可视化电力监控运维平台 想…

jpg压缩在线方法,我只用这2种(无损)

在数字化的时代&#xff0c;我们经常需要分享、存储或上传各种图像文件&#xff0c;而JPG是其中最常见的图像格式之一。然而&#xff0c;大文件大小有时可能成为一个问题&#xff0c;尤其是在网络传输或存储空间有限的情况下。为了解决这一问题&#xff0c;我们可以利用在线工具…

【嵌入式系统开发】002 VI编辑器入门

文章目录 0. 前言&#xff11;. VI编辑器简介1.1 什么是VI编辑器1.2 打开VI编辑器 2. VI编辑器的三种工作模式间&#xff08;模式切换与部分功能&#xff09;3. 移动操作4. 编辑4.1 插入4.2 删除 5. 复制、粘贴6. 查找、替换 0. 前言 对文件进行编辑时&#xff0c;如果是在有图…

gsoap2.8交叉编译方法(详细、亲测可用)

环境搭建 交叉编译器安装&#xff0c;过程略。 注意&#xff1a;如果要使用脚本配置环境变量&#xff0c;在运行脚本时&#xff0c;应该使用 . /绝对路径的方式&#xff0c;而不是直接/绝对路径或者./绝对路径&#xff0c;否则会导致配置失败。&#xff08;亲测如此&#xff0…

[巨详细]安装HBuilder-X教程

文章目录 下载HBuilder-X点击网址 &#xff0c;打开官网先点击所有产品&#xff0c;再点击HBuilder-X。进入HBuilder-X官网页面点击more&#xff0c;选择适合的版本下载。等待下载打开压缩包&#xff0c;点击HBuilderX.exe选择喜欢的风格关闭该弹窗&#xff0c;选择创建就创建成…

如何学习 Java 中的 Socket 编程,进行网络通信

Socket编程是网络编程的核心技术之一&#xff0c;它使得不同主机之间可以进行数据通信。Java提供了丰富的网络编程API&#xff0c;使得编写网络应用程序变得相对简单和直观。本文将详细讲解如何学习Java中的Socket编程&#xff0c;并通过示例代码展示如何实现网络通信。 一、S…

Java情侣飞行棋系统小程序+H5+微信公众号+APP 源码

&#x1f491;甜蜜互动&#xff0c;共赴云端之旅&#x1f6eb; &#x1f308;一、引言&#xff1a;飞行棋遇上情侣&#xff0c;乐趣翻倍 在繁忙的生活中&#xff0c;情侣们总是渴望找到一种简单而有趣的方式来增进彼此的感情。这时&#xff0c;情侣飞行棋小程序应运而生&#…

视频融合共享平台LntonCVS视频监控管理平台技术方案详细介绍

LntonCVS国标视频综合管理平台是一款以视频为核心的智慧物联应用平台。它基于分布式、负载均衡等流媒体技术进行开发&#xff0c;提供广泛兼容、安全可靠、开放共享的视频综合服务。该平台具备多种功能&#xff0c;包括视频直播、录像、回放、检索、云存储、告警上报、语音对讲…

【C#】汽车租赁系统设计与实现

目的&#xff1a; 设计一个简单的汽车租赁系统&#xff0c;包含以下功能&#xff1a; 添加车辆&#xff1a;用户可以添加新的车辆到系统中&#xff0c;包括车辆的品牌、型号、车牌号、日租金等信息。查找车辆&#xff1a;用户可以通过车牌号或者品牌来查找车辆&#xff0c;并…

MyBatis查询两个字段,返回Map,一个字段作为key,一个字段作为value的实现

项目场景&#xff1a; 在使用MyBatis&#xff0c;我们经常会遇到这种情况&#xff1a;SELECT两个字段&#xff0c;需要返回一个Map&#xff0c;其中第一个字段作为key&#xff0c;第二个字段作为value。MyBatis的MapKey虽然很实用&#xff0c;但并不能解决这种场景。 问题描述 …

【Unity】向量应用:已知入射方向和法向量求反射方向(跳弹系统)

文章目录 已知入射方向和法向量求反射方向已知条件解题思路代码范例 已知入射方向和法向量求反射方向 已知条件 已知入射向量v1和法向量n&#xff08;OB&#xff09;&#xff0c;求反射向量v2&#xff0c;上述向量均为单位向量。 解题思路 设 AO为 v1 &#xff1b;OB为 n …