Springboot+Mybatis-plus自动生成代码

前言

Mybatis-Plus是一个优秀的Mybatis增强工具,Mybatis-Plus原生提供了很多单表操作的方法,极大简化了繁琐的curd的操作,同时又支持xml配置、自定义sql的编写。这篇文章介绍SpringBoot2集成Mybatis-Plus 3.1.0,同时介绍mybatis提供MysqlGenerator.java,你可以通过指定的数据库表生成对应的entity、mapper.xml、mapper.java、service.java、serviceImpl.java,和controller。

第一步:pom.xml配置

 <properties>
        <java.version>1.8</java.version>
        <mybatis.version>1.3.0</mybatis.version>
        <druid.version>1.1.10</druid.version>
        <mysql.version>5.1.38</mysql.version>
</properties>
<dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </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>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>
        <dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>${mybatis.version}</version>
        </dependency>
        <!--mybatis-plus-->
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>2.3</version>
        </dependency>
        <!-- mybatis plus 代码生成器依赖 -->
        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-generator</artifactId>
            <version>3.1.0</version>
        </dependency>
        <!-- 模板引擎(此处用的是freemaker,可以根据自己的需要选择模板引擎) -->
        <dependency>
            <groupId>org.freemarker</groupId>
            <artifactId>freemarker</artifactId>
            <version>2.3.28</version>
        </dependency>
        <!--数据库连接池-->
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>druid</artifactId>
            <version>${druid.version}</version>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <version>1.18.12</version>
            <scope>provided</scope>
        </dependency>

        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-lang3</artifactId>
            <version>3.9</version>
        </dependency>
        
        <dependency>
            <groupId>cn.hutool</groupId>
            <artifactId>hutool-all</artifactId>
            <version>5.2.1</version>
        </dependency>


    </dependencies>

第二步:配置application.yml

server:
  port: 8080

#数据库配置
spring:
  datasource:
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://localhost:3306/test_order?useUnicode=true&useSSL=false&characterEncoding=utf8
    username: root
    password: root

mybatis-plus:
  mapper-locations: com/ysw/shardingsphere/core/mapper

第三步:配置代码生成器MysqlGenerator

package com.ysw.shardingsphere.util;

import cn.hutool.core.util.StrUtil;
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 com.baomidou.mybatisplus.toolkit.MapUtils;
import com.google.common.collect.Maps;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.jdbc.core.JdbcOperations;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.SingleColumnRowMapper;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.util.CollectionUtils;

import javax.sql.DataSource;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * @Author ysw
 * @Dcscription:代码生成类
 * @Date 2020/3/12 0012 15:37
 */
public class MysqlGenerator {
    private static Logger logger = LoggerFactory.getLogger(MysqlGenerator.class);

    private static final String database = "test_order";
    private static final String url = "jdbc:mysql://localhost:3306/" + database
            + "?useUnicode=true&useSSL=false&characterEncoding=utf8";
    private static final String driverName = "com.mysql.jdbc.Driver";
    private static final String userName = "root";
    private static final String password = "221317";

    private static String basePath = "";
    private static String mapperPath = "";

    public static void main(String[] args) {
        generate("ysw","com.ysw.shardingsphere.core", "t");
    }

    /**
     * @param
     * @Description:自动生成代码
     * @Author: ysw
     * @Return void
     * @Date: 2020/03/12 15:42
     */
    public static void generate(String author, String packageName, String... tablePrefix) {
        // 全局配置
        GlobalConfig gc = initGlobalConfig(author, packageName);
        // 数据源配置
        DataSourceConfig dsc = initDataSourceConfig();
        // 包配置,设置生成的文件放到哪个包下面
        PackageConfig pc = new PackageConfig()
                .setParent(packageName)
                .setController("controller");
        // 模板引擎配置
        FreemarkerTemplateEngine templateEngine = new FreemarkerTemplateEngine();

        //每一个entity都需要单独设置InjectionConfig, StrategyConfig和TemplateConfig
        Map<String, String> names = new JdbcRepository().getEntityNames(tablePrefix);
        if (MapUtils.isEmpty(names)) {
            return;
        }
        for (String tableName : names.keySet()) {
            // 代码生成器
            AutoGenerator mpg = new AutoGenerator();
            mpg.setGlobalConfig(gc);
            mpg.setDataSource(dsc);
            mpg.setPackageInfo(pc);
            mpg.setTemplateEngine(templateEngine);
            // 自定义配置
            InjectionConfig cfg = initInjectionConfig(packageName);
            mpg.setCfg(cfg);
            // 策略配置
            StrategyConfig strategy = initStrategyConfig(tableName, tablePrefix);
            mpg.setStrategy(strategy);
            // 模板配置
            // mapper文件
            String mapperFile = mapperPath
                    + "/" + names.get(tableName) + "Mapper.java";
            TemplateConfig tc = initTemplateConfig(mapperFile);
            mpg.setTemplate(tc);
            //开始执行
            mpg.execute();
        }

    }

    /**
     * @param
     * @Description:配置数据源
     * @Author: ysw
     * @Return com.baomidou.mybatisplus.generator.config.DataSourceConfig
     * @Date: 2020/03/12 16:22
     */
    private static DataSourceConfig initDataSourceConfig() {
        return new DataSourceConfig()
                .setUrl(url)
                .setDriverName(driverName)
                .setUsername(userName)
                .setPassword(password);
    }

    /**
     * @param author
     * @Description:全局配置
     * @Author: ysw
     * @Return com.baomidou.mybatisplus.generator.config.GlobalConfig
     * @Date: 2020/03/12 16:27
     */
    private static GlobalConfig initGlobalConfig(String author, String packageName) {
        GlobalConfig gc = new GlobalConfig();
        String tmp = MysqlGenerator.class.getResource("").getPath();
        String codeDir = StringUtils.truncate(tmp, tmp.indexOf("/target"));
        basePath = codeDir + "/src/main/java";
        mapperPath = basePath + "/" + packageName.replace(".", "/") + "/mapper";
        System.out.println("basePath = " + basePath + "\nmapperPath = " + mapperPath);
        gc.setOutputDir(basePath);
        gc.setAuthor(author);
        gc.setOpen(false);
        gc.setServiceName("%sService");
        gc.setFileOverride(true);
        return gc;
    }

    /**
     * @param packageName
     * @Description:自定义配置
     * @Author: ysw
     * @Return com.baomidou.mybatisplus.generator.InjectionConfig
     * @Date: 2020/03/12 16:28
     */
    private static InjectionConfig initInjectionConfig(String packageName) {
        InjectionConfig cfg = new InjectionConfig() {
            @Override
            public void initMap() {

            }
        };
        List<FileOutConfig> focList = new ArrayList<>();
        focList.add(new FileOutConfig("/templates/mapper.xml.ftl") {
            @Override
            public String outputFile(TableInfo tableInfo) {
                //自定义输入文件名称
                return mapperPath
                        + "/" + tableInfo.getEntityName() + "Mapper.xml";
            }
        });
        cfg.setFileOutConfigList(focList);
        return cfg;
    }

    /**
     * @param tableName
     * @Description:策略配置
     * @Author: ysw
     * @Return com.baomidou.mybatisplus.generator.config.StrategyConfig
     * @Date: 2020/03/12 16:32
     */
    private static StrategyConfig initStrategyConfig(String tableName, String... tablePrefix) {
        StrategyConfig strategy = new StrategyConfig();
        strategy.setNaming(NamingStrategy.underline_to_camel);
        strategy.setColumnNaming(NamingStrategy.underline_to_camel);
        strategy.setEntityLombokModel(true);
        strategy.setTablePrefix(tablePrefix);
        strategy.setInclude(tableName);
        strategy.setRestControllerStyle(true);
        return strategy;
    }

    /**
     * @param mapperFile
     * @Description:覆盖entity及xml
     * @Author: ysw
     * @Return com.baomidou.mybatisplus.generator.config.TemplateConfig
     * @Date: 2020/03/12 16:35
     */
    private static TemplateConfig initTemplateConfig(String mapperFile) {
        TemplateConfig templateConfig = new TemplateConfig();
        templateConfig.setXml(null);
        //如果当前Entity已经存在,那么仅仅覆盖Entity
        File file = new File(mapperFile);
        if (file.exists()) {
            templateConfig.setController(null);
            templateConfig.setMapper(null);
            templateConfig.setService(null);
            templateConfig.setServiceImpl(null);
            templateConfig.setEntity(null);
        }
        return templateConfig;
    }

    public static class JdbcRepository {
        private static Pattern linePattern = Pattern.compile("_(\\w)");
        private JdbcOperations jdbcOperations;
        /**
          * @Description:数据库连接池
          * @Author: ysw
          * @param 
          * @Return 
          * @Date: 2020/03/12 17:38
          */
        public JdbcRepository() {
            DataSource dataSource = DataSourceBuilder.create()
                    //如果不指定类型,那么默认使用连接池,会存在连接不能回收而最终被耗尽的问题
                    .type(DriverManagerDataSource.class)
                    .driverClassName(driverName)
                    .url(url)
                    .username(userName)
                    .password(password)
                    .build();
            this.jdbcOperations = new JdbcTemplate(dataSource);
        }
        /**
          * @Description:获取所有实体类的名字,实体类由数据库表名转换而来,例如: 表前缀为auth,完整表名为auth_first_second,那么entity则为FirstSecond
          * @Author: ysw
          * @param tablePrefixArray
          * @Return java.util.Map<java.lang.String,java.lang.String>
          * @Date: 2020/03/12 17:38
          */
        public Map<String, String> getEntityNames(String... tablePrefixArray) {
            //该sql语句目前支持mysql
            String sql = "SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_schema = '" + database + "'";
            if (tablePrefixArray != null && tablePrefixArray.length != 0) {
                if (tablePrefixArray.length > 1) {
                    sql += "and ( ";
                    for (String prefix : tablePrefixArray) {
                        sql += " table_name like '" + prefix + "_%' or ";
                    }
                    sql += ")";
                    sql = StrUtil.replace(sql, sql.lastIndexOf("or"), sql.lastIndexOf("or") + 3, ' ');
                } else {
                    sql += " and table_name like '" + tablePrefixArray[0] + "_%'";
                }
            }
            List<String> tableNames = jdbcOperations.query(sql, SingleColumnRowMapper.newInstance(String.class));
            if (CollectionUtils.isEmpty(tableNames)) {
                return Maps.newHashMap();
            }
            Map<String, String> result = Maps.newHashMap();
            tableNames.forEach(
                    tableName -> {
                        String entityName = underlineToCamel(tableName);
                        if (tablePrefixArray != null && tablePrefixArray.length != 0) {
                            for (String prefix : tablePrefixArray) {
                                //如果有前缀,需要去掉前缀
                                if (tableName.startsWith(prefix)) {
                                    String tableNameRemovePrefix = tableName.substring((prefix + "_").length());
                                    entityName = underlineToCamel(tableNameRemovePrefix);
                                }
                            }
                        }
                        result.put(tableName, entityName);
                    }
            );
            return result;
        }
        /**
          * @Description:下划线转驼峰
          * @Author: ysw
          * @param str
          * @Return java.lang.String
          * @Date: 2020/03/12 17:37
          */
        private static String underlineToCamel(String str) {
            if (StringUtils.isBlank(str)) {
                return str;
            }
            str = str.toLowerCase();
            Matcher matcher = linePattern.matcher(str);
            StringBuffer sb = new StringBuffer();
            while (matcher.find()) {
                matcher.appendReplacement(sb, matcher.group(1).toUpperCase());
            }
            matcher.appendTail(sb);
            str = sb.toString();
            str = str.substring(0, 1).toUpperCase() + str.substring(1);
            return str;
        }
    }

}

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值