本篇文章实现了由模板一键生成 entity、controller、service、dao 相关类
dao 层主要是基于 Hibernate 框架和 PostgreSQL 数据库。
# 项目结构
- 新建 maven 项目,删除所有生成的文件,只留下 pom.xml,作为总项目。
- 在当前项目下,新建一个 maven 子模块,取名为 base 模块,包含基础类以及下面自动生成类的相关实现也放在此模块中。
- 在当前项目下,新建一个 maven 子模块,取名为 business 模块,包含相关业务实现类。
- 在 business 新建四个模块,分别为 business-entity、business-dao、business-service、business-controller 模块。
- 在 business 模块中需要引入 base 模块依赖。
在总项目 pom.xml 中引入所需依赖
<dependencies> | |
<dependency> | |
<groupId>org.apache.commons</groupId> | |
<artifactId>commons-lang3</artifactId> | |
<version>3.10</version> | |
</dependency> | |
<dependency> | |
<groupId>ch.qos.logback</groupId> | |
<artifactId>logback-core</artifactId> | |
<version>1.2.11</version> | |
</dependency> | |
<dependency> | |
<groupId>ch.qos.logback</groupId> | |
<artifactId>logback-classic</artifactId> | |
<version>1.2.11</version> | |
</dependency> | |
<dependency> | |
<groupId>org.slf4j</groupId> | |
<artifactId>slf4j-api</artifactId> | |
<version>1.7.32</version> | |
</dependency> | |
<dependency> | |
<groupId>org.freemarker</groupId> | |
<artifactId>freemarker</artifactId> | |
<version>2.3.29</version> | |
</dependency> | |
<dependency> | |
<groupId>io.swagger</groupId> | |
<artifactId>swagger-annotations</artifactId> | |
<version>1.6.5</version> | |
</dependency> | |
<dependency> | |
<groupId>org.hibernate</groupId> | |
<artifactId>hibernate-core</artifactId> | |
<version>5.6.7.Final</version> | |
</dependency> | |
<dependency> | |
<groupId>org.springframework.data</groupId> | |
<artifactId>spring-data-jpa</artifactId> | |
<version>2.6.3</version> | |
</dependency> | |
<dependency> | |
<groupId>org.springframework.boot</groupId> | |
<artifactId>spring-boot-starter-data-jpa</artifactId> | |
<version>2.6.6</version> | |
</dependency> | |
<dependency> | |
<groupId>org.postgresql</groupId> | |
<artifactId>postgresql</artifactId> | |
<version>42.3.3</version> | |
</dependency> | |
<dependency> | |
<groupId>org.springframework.boot</groupId> | |
<artifactId>spring-boot-starter-web</artifactId> | |
<version>2.6.6</version> | |
</dependency> | |
</dependencies> |
# 配置常量类
新建包名 com.qiyin.base.generator.config,当前下的所有类都放在这个包下面。
ConstVal
package com.qiyin.base.generator.config; | |
import java.nio.charset.StandardCharsets; | |
/** | |
* 常量 | |
**/ | |
public interface ConstVal { | |
String KT_SUFFIX = ".kt"; | |
String JAVA_SUFFIX = ".java"; | |
String MODULE_NAME = "ModuleName"; | |
String ENTITY = "Entity"; | |
String DAO = "Dao"; | |
String DAO_IMPL = "DaoImpl"; | |
String SERVICE = "Service"; | |
String SERVICE_IMPL = "ServiceImpl"; | |
String CONTROLLER = "Controller"; | |
String ENTITY_PATH = "entity_path"; | |
String DAO_PATH = "dao_path"; | |
String DAO_IMPL_PATH = "dao_impl_path"; | |
String SERVICE_PATH = "service_path"; | |
String SERVICE_IMPL_PATH = "service_impl_path"; | |
String CONTROLLER_PATH = "controller_path"; | |
String JAVA_TMPDIR = "java.io.tmpdir"; | |
String UTF8 = StandardCharsets.UTF_8.name(); | |
String TEMPLATE_ENTITY = "/templates/entity.java"; | |
String TEMPLATE_DAO = "/templates/dao.java"; | |
String TEMPLATE_DAO_IMPL = "/templates/daoImpl.java"; | |
String TEMPLATE_SERVICE = "/templates/service.java"; | |
String TEMPLATE_SERVICE_IMPL = "/templates/serviceImpl.java"; | |
String TEMPLATE_CONTROLLER = "/templates/controller.java"; | |
String MODEL_NORMAL = "normal"; | |
String MODEL_OTHER = "other"; | |
} |
StringVal
package com.qiyin.base.generator.config; | |
/** | |
* 字符串常用常量 | |
*/ | |
public interface StringVal { | |
String AMPERSAND = "&"; | |
String AND = "and"; | |
String AT = "@"; | |
String ASTERISK = "*"; | |
String STAR = ASTERISK; | |
String BACK_SLASH = "\\"; | |
String COLON = ":"; | |
String COMMA = ","; | |
String DASH = "-"; | |
String DOLLAR = "$"; | |
String DOT = "."; | |
String DOTDOT = ".."; | |
String DOT_CLASS = ".class"; | |
String DOT_JAVA = ".java"; | |
String DOT_XML = ".xml"; | |
String EMPTY = ""; | |
String EQUALS = "="; | |
String FALSE = "false"; | |
String SLASH = "/"; | |
String HASH = "#"; | |
String HAT = "^"; | |
String LEFT_BRACE = "{"; | |
String LEFT_BRACKET = "("; | |
String LEFT_CHEV = "<"; | |
String DOT_NEWLINE = ",\n"; | |
String NEWLINE = "\n"; | |
String N = "n"; | |
String NO = "no"; | |
String NULL = "null"; | |
String OFF = "off"; | |
String ON = "on"; | |
String PERCENT = "%"; | |
String PIPE = "|"; | |
String PLUS = "+"; | |
String QUESTION_MARK = "?"; | |
String EXCLAMATION_MARK = "!"; | |
String QUOTE = "\""; | |
String RETURN = "\r"; | |
String TAB = "\t"; | |
String RIGHT_BRACE = "}"; | |
String RIGHT_BRACKET = ")"; | |
String RIGHT_CHEV = ">"; | |
String SEMICOLON = ";"; | |
String SINGLE_QUOTE = "'"; | |
String BACKTICK = "`"; | |
String SPACE = " "; | |
String TILDA = "~"; | |
String LEFT_SQ_BRACKET = "["; | |
String RIGHT_SQ_BRACKET = "]"; | |
String TRUE = "true"; | |
String UNDERSCORE = "_"; | |
String UTF_8 = "UTF-8"; | |
String US_ASCII = "US-ASCII"; | |
String ISO_8859_1 = "ISO-8859-1"; | |
String Y = "y"; | |
String YES = "yes"; | |
String ONE = "1"; | |
String ZERO = "0"; | |
String DOLLAR_LEFT_BRACE = "${"; | |
String HASH_LEFT_BRACE = "#{"; | |
String CRLF = "\r\n"; | |
String HTML_NBSP = " "; | |
String HTML_AMP = "&"; | |
String HTML_QUOTE = """; | |
String HTML_LT = "<"; | |
String HTML_GT = ">"; | |
} |
GlobalConfig
package com.qiyin.base.generator.config; | |
/** | |
* 全局配置 | |
*/ | |
public class GlobalConfig { | |
private boolean kotlin = false; | |
/** | |
* 是否覆盖已有文件 | |
*/ | |
private boolean fileOverride = true; | |
/** | |
* 生成文件的输出目录【默认 D 盘根目录】 | |
*/ | |
private String outputDir = "D://"; | |
private String author; | |
private String tableName; | |
private String project; | |
private String comment; | |
/** | |
* 数据库模式 | |
*/ | |
private String schema; | |
/** | |
* 数据表 | |
*/ | |
private String dataTableName; | |
/** | |
* 数据表前缀 | |
*/ | |
private String dataTablePrefix; | |
/** | |
* 生成类型. | |
* normal: 正常 | |
*/ | |
private String classType = ConstVal.MODEL_NORMAL; | |
public boolean isKotlin() { | |
return kotlin; | |
} | |
public GlobalConfig setKotlin(boolean kotlin) { | |
this.kotlin = kotlin; | |
return this; | |
} | |
public boolean isFileOverride() { | |
return fileOverride; | |
} | |
public GlobalConfig setFileOverride(boolean fileOverride) { | |
this.fileOverride = fileOverride; | |
return this; | |
} | |
public String getOutputDir() { | |
return outputDir; | |
} | |
public GlobalConfig setOutputDir(String outputDir) { | |
this.outputDir = outputDir; | |
return this; | |
} | |
public String getAuthor() { | |
return author; | |
} | |
public GlobalConfig setAuthor(String author) { | |
this.author = author; | |
return this; | |
} | |
public String getTableName() { | |
return tableName; | |
} | |
public GlobalConfig setTableName(String tableName) { | |
this.tableName = tableName; | |
return this; | |
} | |
public String getProject() { | |
return project; | |
} | |
public GlobalConfig setProject(String project) { | |
this.project = project; | |
return this; | |
} | |
public String getComment() { | |
return comment; | |
} | |
public GlobalConfig setComment(String comment) { | |
this.comment = comment; | |
return this; | |
} | |
public String getClassType() { | |
return classType; | |
} | |
public GlobalConfig setClassType(String classType) { | |
this.classType = classType; | |
return this; | |
} | |
public GlobalConfig setSchema(String schema) { | |
this.schema = schema; | |
return this; | |
} | |
public GlobalConfig setDataTableName(String dataTableName) { | |
this.dataTableName = dataTableName; | |
return this; | |
} | |
public GlobalConfig setDataTablePrefix(String dataTablePrefix) { | |
this.dataTablePrefix = dataTablePrefix; | |
return this; | |
} | |
public String getSchema() { | |
return schema; | |
} | |
public String getDataTableName() { | |
return dataTableName; | |
} | |
public String getDataTablePrefix() { | |
return dataTablePrefix; | |
} | |
} |
PackageConfig
package com.qiyin.base.generator.config; | |
import java.util.Map; | |
public class PackageConfig { | |
private String parent = ""; | |
/** | |
* 生成实体在那个包下. | |
*/ | |
private String packageName = ""; | |
private String entity = "entity"; | |
private String dao = "dao"; | |
private String daoImpl = "dao"; | |
private String service = "service"; | |
private String serviceImpl = "service.impl"; | |
private String controller = "controller"; | |
/** | |
* 路径配置信息 | |
*/ | |
private Map<String, String> pathInfo; | |
public String getParent() { | |
return parent; | |
} | |
public PackageConfig setParent(String parent) { | |
this.parent = parent; | |
return this; | |
} | |
public String getPackageName() { | |
return packageName; | |
} | |
public PackageConfig setPackageName(String packageName) { | |
this.packageName = packageName; | |
return this; | |
} | |
public String getEntity() { | |
return entity; | |
} | |
public PackageConfig setEntity(String entity) { | |
this.entity = entity; | |
return this; | |
} | |
public String getDao() { | |
return dao; | |
} | |
public PackageConfig setDao(String repository) { | |
this.dao = repository; | |
return this; | |
} | |
public String getDaoImpl() { | |
return daoImpl; | |
} | |
public PackageConfig setDaoImpl(String daoImpl) { | |
this.daoImpl = daoImpl; | |
return this; | |
} | |
public String getService() { | |
return service; | |
} | |
public PackageConfig setService(String service) { | |
this.service = service; | |
return this; | |
} | |
public String getServiceImpl() { | |
return serviceImpl; | |
} | |
public PackageConfig setServiceImpl(String serviceImpl) { | |
this.serviceImpl = serviceImpl; | |
return this; | |
} | |
public String getController() { | |
return controller; | |
} | |
public PackageConfig setController(String controller) { | |
this.controller = controller; | |
return this; | |
} | |
public Map<String, String> getPathInfo() { | |
return pathInfo; | |
} | |
public PackageConfig setPathInfo(Map<String, String> pathInfo) { | |
this.pathInfo = pathInfo; | |
return this; | |
} | |
} |
TemplateConfig
package com.qiyin.base.generator.config; | |
/** | |
* 模板路径配置 | |
**/ | |
public class TemplateConfig { | |
private String entity = ConstVal.TEMPLATE_ENTITY; | |
private String dao = ConstVal.TEMPLATE_DAO; | |
private String daoImpl = ConstVal.TEMPLATE_DAO_IMPL; | |
private String service = ConstVal.TEMPLATE_SERVICE; | |
private String serviceImpl = ConstVal.TEMPLATE_SERVICE_IMPL; | |
private String controller = ConstVal.TEMPLATE_CONTROLLER; | |
public String getEntity() { | |
return entity; | |
} | |
public void setEntity(String entity) { | |
this.entity = entity; | |
} | |
public String getDao() { | |
return dao; | |
} | |
public void setDao(String dao) { | |
this.dao = dao; | |
} | |
public String getDaoImpl() { | |
return daoImpl; | |
} | |
public void setDaoImpl(String daoImpl) { | |
this.daoImpl = daoImpl; | |
} | |
public String getService() { | |
return service; | |
} | |
public void setService(String service) { | |
this.service = service; | |
} | |
public String getServiceImpl() { | |
return serviceImpl; | |
} | |
public void setServiceImpl(String serviceImpl) { | |
this.serviceImpl = serviceImpl; | |
} | |
public String getController() { | |
return controller; | |
} | |
public void setController(String controller) { | |
this.controller = controller; | |
} | |
} |
# 临时表
新建包名 com.qiyin.base.generator.dto,当前下的所有类都放在这个包下面。
TableInfo
package com.qiyin.base.generator.dto; | |
import java.util.HashSet; | |
import java.util.Set; | |
/** | |
* 表信息,关联到当前字段信息 | |
*/ | |
public class TableInfo { | |
private Set<String> importPackages = new HashSet<>(); | |
private String name; | |
private String entityName; | |
private String daoName; | |
private String daoImplName; | |
private String serviceName; | |
private String serviceImplName; | |
private String controllerName; | |
/** | |
* 数据库模式 | |
*/ | |
private String schema; | |
/** | |
* 数据库 | |
*/ | |
private String tableName; | |
/** | |
* 字段前缀 | |
*/ | |
private String tablePrefix; | |
public void setImportPackages(String pkg) { | |
importPackages.add(pkg); | |
} | |
public Set<String> getImportPackages() { | |
return importPackages; | |
} | |
public String getName() { | |
return name; | |
} | |
public void setName(String name) { | |
this.name = name; | |
} | |
public String getEntityName() { | |
return entityName; | |
} | |
public void setEntityName(String entityName) { | |
this.entityName = entityName; | |
} | |
public String getDaoName() { | |
return daoName; | |
} | |
public void setDaoName(String daoName) { | |
this.daoName = daoName; | |
} | |
public String getDaoImplName() { | |
return daoImplName; | |
} | |
public void setDaoImplName(String daoImplName) { | |
this.daoImplName = daoImplName; | |
} | |
public String getServiceName() { | |
return serviceName; | |
} | |
public void setServiceName(String serviceName) { | |
this.serviceName = serviceName; | |
} | |
public String getServiceImplName() { | |
return serviceImplName; | |
} | |
public void setServiceImplName(String serviceImplName) { | |
this.serviceImplName = serviceImplName; | |
} | |
public String getControllerName() { | |
return controllerName; | |
} | |
public void setControllerName(String controllerName) { | |
this.controllerName = controllerName; | |
} | |
public String getSchema() { | |
return schema; | |
} | |
public void setSchema(String schema) { | |
this.schema = schema; | |
} | |
public String getTableName() { | |
return tableName; | |
} | |
public void setTableName(String tableName) { | |
this.tableName = tableName; | |
} | |
public String getTablePrefix() { | |
return tablePrefix; | |
} | |
public void setTablePrefix(String tablePrefix) { | |
this.tablePrefix = tablePrefix; | |
} | |
} |
# 配置汇总
新建包名 com.qiyin.base.generator.builder,当前下的所有类都放在这个包下面。
ConfigBuilder
package com.qiyin.base.generator.builder; | |
import com.qiyin.base.controller.AbstractController; | |
import com.qiyin.base.dao.AbstractDao; | |
import com.qiyin.base.dao.AbstractDaoImpl; | |
import com.qiyin.base.entity.AbstractEntity; | |
import com.qiyin.base.generator.config.ConstVal; | |
import com.qiyin.base.generator.config.GlobalConfig; | |
import com.qiyin.base.generator.config.PackageConfig; | |
import com.qiyin.base.generator.config.StringVal; | |
import com.qiyin.base.generator.config.TemplateConfig; | |
import com.qiyin.base.generator.dto.TableInfo; | |
import com.qiyin.base.service.AbstractService; | |
import com.qiyin.base.service.AbstractServiceImpl; | |
import org.apache.commons.lang3.StringUtils; | |
import java.io.File; | |
import java.util.ArrayList; | |
import java.util.HashMap; | |
import java.util.List; | |
import java.util.Map; | |
/** | |
* 配置汇总 传递给文件生成工具 | |
**/ | |
public class ConfigBuilder { | |
/** | |
* 模板路径配置信息 | |
*/ | |
private final TemplateConfig template; | |
private String superEntityClass; | |
private String superDaoClass; | |
private String superDaoImplClass; | |
private String superServiceClass; | |
private String superServiceImplClass; | |
private String superControllerClass; | |
/** | |
* 全局配置信息 | |
*/ | |
private GlobalConfig globalConfig; | |
/** | |
* 包配置详情 | |
*/ | |
private Map<String, String> packageInfo; | |
/** | |
* 路径配置信息 | |
*/ | |
private Map<String, String> pathInfo; | |
/** | |
* 数据库表信息 | |
*/ | |
private List<TableInfo> tableInfoList; | |
/** | |
* 在构造器中处理配置 | |
* | |
* @param packageConfig 包配置 | |
* @param template 模板配置 | |
* @param globalConfig 全局配置 | |
*/ | |
public ConfigBuilder(PackageConfig packageConfig, | |
TemplateConfig template, GlobalConfig globalConfig) { | |
this.globalConfig = globalConfig == null ? new GlobalConfig() :globalConfig; | |
this.template = template == null ? new TemplateConfig() : template; | |
handlerPackage(packageConfig == null ? new PackageConfig() : packageConfig); | |
handlerTable(); | |
handlerSuperClass(); | |
} | |
/** | |
* 处理包配置 | |
* | |
* @param config 包配置 | |
*/ | |
private void handlerPackage(PackageConfig config) { | |
if (StringUtils.isBlank(config.getParent())){ | |
String parent = "com.example." + this.globalConfig.getProject().replace("qiyin-", ""); // | |
config.setParent(parent); | |
} | |
String moduleName = config.getPackageName(); | |
packageInfo = new HashMap<>(8); | |
packageInfo.put(ConstVal.MODULE_NAME, moduleName); | |
packageInfo.put(ConstVal.ENTITY, joinPackage(config.getParent() + "." + config.getEntity(), moduleName)); | |
packageInfo.put(ConstVal.DAO, joinPackage(config.getParent() + "." + config.getDao(), moduleName)); | |
packageInfo.put(ConstVal.DAO_IMPL, joinPackage(config.getParent() + "." + config.getDaoImpl(), moduleName)); | |
packageInfo.put(ConstVal.SERVICE, joinPackage(config.getParent() + "." + config.getService(), moduleName)); | |
packageInfo.put(ConstVal.SERVICE_IMPL, joinPackage(config.getParent() + "." + config.getServiceImpl(), moduleName)); // | |
packageInfo.put(ConstVal.CONTROLLER, joinPackage(config.getParent() + "." + config.getController(), moduleName)); | |
// 自定义路径 | |
Map<String, String> configPathInfo = config.getPathInfo(); | |
if (configPathInfo != null){ | |
pathInfo = configPathInfo; | |
return; | |
} | |
String outputDir = this.globalConfig.getOutputDir(); | |
// 生成路径信息 | |
pathInfo = new HashMap<>(8); | |
setPathInfo(pathInfo, outputDir, ConstVal.ENTITY_PATH, ConstVal.ENTITY); | |
setPathInfo(pathInfo, outputDir, ConstVal.DAO_PATH, ConstVal.DAO); | |
setPathInfo(pathInfo, outputDir, ConstVal.DAO_IMPL_PATH, ConstVal.DAO_IMPL); | |
setPathInfo(pathInfo, outputDir, ConstVal.SERVICE_PATH, ConstVal.SERVICE); | |
setPathInfo(pathInfo, outputDir, ConstVal.SERVICE_IMPL_PATH, ConstVal.SERVICE_IMPL); | |
setPathInfo(pathInfo, outputDir, ConstVal.CONTROLLER_PATH, ConstVal.CONTROLLER); | |
} | |
/** | |
* 处理表相关类名称 | |
*/ | |
private void handlerTable() { | |
tableInfoList = new ArrayList<>(); | |
String[] tables = StringUtils.split(this.globalConfig.getTableName(), StringVal.COMMA); | |
for (String table : tables){ | |
TableInfo tableInfo = new TableInfo(); | |
String entityName = table + "Entity"; | |
tableInfo.setName(table); | |
tableInfo.setEntityName(entityName); | |
tableInfo.setDaoName(table + ConstVal.DAO); | |
tableInfo.setDaoImplName(table + ConstVal.DAO_IMPL); | |
tableInfo.setServiceName(table + ConstVal.SERVICE); | |
tableInfo.setServiceImplName(table + ConstVal.SERVICE_IMPL); | |
tableInfo.setControllerName(table + ConstVal.CONTROLLER); | |
tableInfoList.add(tableInfo); | |
} | |
} | |
/** | |
* 处理父类 | |
*/ | |
private void handlerSuperClass() { | |
switch (globalConfig.getClassType()){ | |
case ConstVal.MODEL_NORMAL: | |
this.superEntityClass = AbstractEntity.class.getName(); | |
this.superDaoClass = AbstractDao.class.getName(); | |
this.superDaoImplClass = AbstractDaoImpl.class.getName(); | |
this.superServiceClass = AbstractService.class.getName(); | |
this.superServiceImplClass = AbstractServiceImpl.class.getName(); | |
this.superControllerClass = AbstractController.class.getName(); | |
break; | |
case ConstVal.MODEL_OTHER: | |
this.superEntityClass = null; | |
this.superDaoClass = null; | |
this.superDaoImplClass = null; | |
this.superServiceClass = null; | |
this.superServiceImplClass = null; | |
this.superControllerClass = null; | |
break; | |
default: | |
break; | |
} | |
} | |
private void setPathInfo(Map<String, String> pathInfo, String outputDir, String path, String classPath) { | |
String tempOutputDir = outputDir + StringVal.BACK_SLASH + globalConfig.getProject() + StringVal.BACK_SLASH + globalConfig.getProject(); | |
switch (path){ | |
case ConstVal.ENTITY_PATH: | |
tempOutputDir = tempOutputDir + "-entity"; | |
break; | |
case ConstVal.DAO_PATH: | |
case ConstVal.DAO_IMPL_PATH: | |
tempOutputDir = tempOutputDir + "-dao"; | |
break; | |
case ConstVal.SERVICE_PATH: | |
case ConstVal.SERVICE_IMPL_PATH: | |
tempOutputDir = tempOutputDir + "-service"; | |
break; | |
case ConstVal.CONTROLLER_PATH: | |
tempOutputDir = tempOutputDir + "-controller"; | |
} | |
pathInfo.put(path, joinPath(tempOutputDir , "src.main.java." + packageInfo.get(classPath))); | |
} | |
/** | |
* 连接路径字符串 | |
* | |
* @param parentDir 父目录 | |
* @param packageName 包名 | |
* @return 连接后的路径 | |
*/ | |
private String joinPath(String parentDir, String packageName) { | |
if (StringUtils.isBlank(parentDir)) { | |
parentDir = System.getProperty(ConstVal.JAVA_TMPDIR); | |
} | |
if (!StringUtils.endsWith(parentDir, File.separator)){ | |
parentDir += File.separator; | |
} | |
packageName = packageName.replaceAll("\\.", "\\" + File.separator); | |
return parentDir + packageName; | |
} | |
/** | |
* 连接父子包名 | |
* | |
* @param parentPackage 父包名 | |
* @param subPackage 子包名 | |
* @return 连接后的包名 | |
*/ | |
private String joinPackage(String parentPackage, String subPackage) { | |
if (StringUtils.isBlank(parentPackage)){ | |
return subPackage; | |
} | |
return parentPackage + "." + subPackage; | |
} | |
/** | |
* 所有包配置信息 | |
* | |
* @return 包配置 | |
*/ | |
public Map<String, String> getPackageInfo() { | |
return packageInfo; | |
} | |
/** | |
* 所有路径配置 | |
* | |
* @return 路径配置 | |
*/ | |
public Map<String, String> getPathInfo() { | |
return pathInfo; | |
} | |
public String getSuperEntityClass() { | |
return superEntityClass; | |
} | |
public String getSuperDaoClass() { | |
return superDaoClass; | |
} | |
public String getSuperDaoImplClass() { | |
return superDaoImplClass; | |
} | |
public String getSuperServiceClass() { | |
return superServiceClass; | |
} | |
public String getSuperServiceImplClass() { | |
return superServiceImplClass; | |
} | |
public String getSuperControllerClass() { | |
return superControllerClass; | |
} | |
/** | |
* 模板路径配置信息 | |
* | |
* @return 所以模板路径配置信息 | |
*/ | |
public TemplateConfig getTemplate() { | |
return template == null ? new TemplateConfig() : template; | |
} | |
public GlobalConfig getGlobalConfig() { | |
return globalConfig; | |
} | |
public List<TableInfo> getTableInfoList() { | |
return tableInfoList; | |
} | |
public ConfigBuilder setTableInfoList(List<TableInfo> tableInfoList) { | |
this.tableInfoList = tableInfoList; | |
return this; | |
} | |
} |
# 模板引擎
新建包名 com.qiyin.base.generator.engine,当前下的所有类都放在这个包下面。
AbstractTemplateEngine
package com.qiyin.base.generator.engine; | |
import com.qiyin.base.generator.builder.ConfigBuilder; | |
import com.qiyin.base.generator.config.ConstVal; | |
import com.qiyin.base.generator.config.GlobalConfig; | |
import com.qiyin.base.generator.config.StringVal; | |
import com.qiyin.base.generator.config.TemplateConfig; | |
import com.qiyin.base.generator.dto.TableInfo; | |
import org.apache.commons.lang3.StringUtils; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import java.io.File; | |
import java.text.SimpleDateFormat; | |
import java.util.Date; | |
import java.util.HashMap; | |
import java.util.List; | |
import java.util.Map; | |
/** | |
* 模板引擎抽象类 | |
*/ | |
public abstract class AbstractTemplateEngine { | |
protected static final Logger LOG = LoggerFactory.getLogger(AbstractTemplateEngine.class); | |
/** | |
* 配置信息 | |
*/ | |
private ConfigBuilder configBuilder; | |
/** | |
* 模板引擎初始化 | |
*/ | |
public AbstractTemplateEngine init(ConfigBuilder configBuilder) { | |
this.configBuilder = configBuilder; | |
return this; | |
} | |
/** | |
* 输出 java xml 文件 | |
*/ | |
public AbstractTemplateEngine batchOutput(){ | |
try { | |
List<TableInfo> tables = getConfigBuilder().getTableInfoList(); | |
for (TableInfo table : tables){ | |
Map<String, Object> objectMap = getObjectMap(table); | |
create(table, objectMap); | |
} | |
}catch (Exception e){ | |
LOG.error("无法创建文件,请检查配置信息是否正确!", e); | |
} | |
return this; | |
} | |
private Map<String, Object> getObjectMap(TableInfo table) { | |
Map<String, Object> objectMap = new HashMap<>(32); | |
ConfigBuilder config = getConfigBuilder(); | |
objectMap.put("config", config); | |
objectMap.put("package", config.getPackageInfo()); | |
GlobalConfig globalConfig = config.getGlobalConfig(); | |
objectMap.put("author", globalConfig.getAuthor()); | |
objectMap.put("comment", globalConfig.getComment()); | |
objectMap.put("schema", globalConfig.getSchema()); | |
objectMap.put("tableName", globalConfig.getDataTableName()); | |
objectMap.put("tablePrefix", globalConfig.getDataTablePrefix()); | |
objectMap.put("kotlin", globalConfig.isKotlin()); | |
objectMap.put("date", new SimpleDateFormat("yyyy-MM-dd").format(new Date())); | |
objectMap.put("table", table); | |
objectMap.put("entity", table.getEntityName()); | |
objectMap.put("superEntityClassPackage", config.getSuperEntityClass()); | |
objectMap.put("superEntityClass", getSuperClassName(config.getSuperEntityClass())); | |
objectMap.put("superDaoClassPackage", config.getSuperDaoClass()); | |
objectMap.put("superDaoClass", getSuperClassName(config.getSuperDaoClass())); | |
objectMap.put("superDaoImplClassPackage", config.getSuperDaoImplClass()); | |
objectMap.put("superDaoImplClass", getSuperClassName(config.getSuperDaoImplClass())); | |
objectMap.put("superServiceClassPackage", config.getSuperServiceClass()); | |
objectMap.put("superServiceClass", getSuperClassName(config.getSuperServiceClass())); | |
objectMap.put("superServiceImplClassPackage", config.getSuperServiceImplClass()); | |
objectMap.put("superServiceImplClass", getSuperClassName(config.getSuperServiceImplClass())); | |
objectMap.put("superControllerClassPackage", config.getSuperControllerClass()); | |
objectMap.put("superControllerClass", getSuperClassName(config.getSuperControllerClass())); | |
return objectMap; | |
} | |
private void create(TableInfo table, Map<String, Object> objectMap) throws Exception{ | |
Map<String, String> pathInfo = getConfigBuilder().getPathInfo(); | |
TemplateConfig template = getConfigBuilder().getTemplate(); | |
// Entity.java | |
String entityName = table.getEntityName(); | |
if (entityName != null && pathInfo.get(ConstVal.ENTITY_PATH) != null){ | |
String entityFile = String.format((pathInfo.get(ConstVal.ENTITY_PATH) + File.separator + "%s" + suffixJavaOrKt()), entityName); | |
if (isCreate(entityFile)){ | |
writer(objectMap, templateFilePath(template.getEntity()), entityFile); | |
} | |
} | |
// Dao.java | |
if (null != table.getDaoName() && null != pathInfo.get(ConstVal.DAO_PATH)) { | |
String daoFile = String.format((pathInfo.get(ConstVal.DAO_PATH) + File.separator + table.getDaoName() + suffixJavaOrKt()), entityName); | |
if (isCreate(daoFile)) { | |
writer(objectMap, templateFilePath(template.getDao()), daoFile); | |
} | |
} | |
// DaoImpl.java | |
if (null != table.getDaoImplName() && null != pathInfo.get(ConstVal.DAO_IMPL_PATH)) { | |
String daoImplFile = String.format((pathInfo.get(ConstVal.DAO_IMPL_PATH) + File.separator + table.getDaoImplName() + suffixJavaOrKt()), entityName); | |
if (isCreate(daoImplFile)) { | |
writer(objectMap, templateFilePath(template.getDaoImpl()), daoImplFile); | |
} | |
} | |
// Service.java | |
if (null != table.getServiceName() && null != pathInfo.get(ConstVal.SERVICE_PATH)) { | |
String serviceFile = String.format((pathInfo.get(ConstVal.SERVICE_PATH) + File.separator + table.getServiceName() + suffixJavaOrKt()), entityName); | |
if (isCreate(serviceFile)) { | |
writer(objectMap, templateFilePath(template.getService()), serviceFile); | |
} | |
} | |
// ServiceImpl.java | |
if (null != table.getServiceImplName() && null != pathInfo.get(ConstVal.SERVICE_IMPL_PATH)) { | |
String serviceImplFile = String.format((pathInfo.get(ConstVal.SERVICE_IMPL_PATH) + File.separator + table.getServiceImplName() + suffixJavaOrKt()), entityName); | |
if (isCreate(serviceImplFile)) { | |
writer(objectMap, templateFilePath(template.getServiceImpl()), serviceImplFile); | |
} | |
} | |
// Controller.java | |
if (null != table.getServiceImplName() && null != pathInfo.get(ConstVal.CONTROLLER_PATH)) { | |
String controllerFile = String.format((pathInfo.get(ConstVal.CONTROLLER_PATH) + File.separator + table.getControllerName() + suffixJavaOrKt()), entityName); | |
if (isCreate(controllerFile)) { | |
writer(objectMap, templateFilePath(template.getController()), controllerFile); | |
} | |
} | |
} | |
/** | |
* 检查文件是否存在 | |
* | |
* @param filePath 文件路径 | |
* @return 是否存在 | |
*/ | |
private boolean isCreate(String filePath) { | |
ConfigBuilder config = getConfigBuilder(); | |
// TODO 自定义判断 | |
// 全局判断【默认】 | |
File file = new File(filePath); | |
boolean exists = file.exists(); | |
if (!exists){ | |
file.getParentFile().mkdirs(); | |
} | |
return !exists || getConfigBuilder().getGlobalConfig().isFileOverride(); | |
} | |
public abstract String templateFilePath(String filePath); | |
protected abstract void writer(Map<String, Object> objectMap, String templateFilePath, String entityFile) throws Exception; | |
public AbstractTemplateEngine mkdirs(){ | |
getConfigBuilder().getPathInfo().forEach((key, value) -> { | |
File file = new File(value); | |
if (!file.exists()){ | |
boolean result = file.mkdirs(); | |
if (result){ | |
LOG.info("创建目录:[" + value + "]"); | |
} | |
} | |
}); | |
return this; | |
} | |
private String getSuperClassName(String classPath) { | |
if (StringUtils.isBlank(classPath)){ | |
return null; | |
} | |
return classPath.substring(classPath.lastIndexOf(StringVal.DOT) + 1); | |
} | |
private String suffixJavaOrKt() { | |
return getConfigBuilder().getGlobalConfig().isKotlin() ? ConstVal.KT_SUFFIX : ConstVal.JAVA_SUFFIX; | |
} | |
public ConfigBuilder getConfigBuilder() { | |
return configBuilder; | |
} | |
} |
FreemarkerTemplateEngine
package com.qiyin.base.generator.engine; | |
import com.qiyin.base.generator.builder.ConfigBuilder; | |
import freemarker.template.Configuration; | |
import freemarker.template.Template; | |
import com.qiyin.base.generator.config.ConstVal; | |
import com.qiyin.base.generator.config.StringVal; | |
import java.io.FileOutputStream; | |
import java.io.OutputStreamWriter; | |
import java.util.Map; | |
/** | |
* Freemarker 模板引擎实现文件输出 | |
*/ | |
public class FreemarkerTemplateEngine extends AbstractTemplateEngine { | |
private Configuration configuration; | |
@Override | |
public AbstractTemplateEngine init(ConfigBuilder configBuilder) { | |
super.init(configBuilder); | |
configuration = new Configuration(Configuration.DEFAULT_INCOMPATIBLE_IMPROVEMENTS); | |
configuration.setDefaultEncoding(ConstVal.UTF8); | |
configuration.setClassForTemplateLoading(FreemarkerTemplateEngine.class, StringVal.SLASH); | |
return this; | |
} | |
@Override | |
public String templateFilePath(String filePath) { | |
return filePath + ".ftl"; | |
} | |
@Override | |
protected void writer(Map<String, Object> objectMap, String templateFilePath, String outputFile) throws Exception { | |
Template template = configuration.getTemplate(templateFilePath); | |
try(FileOutputStream fileOutputStream = new FileOutputStream(outputFile)) { | |
template.process(objectMap, new OutputStreamWriter(fileOutputStream, ConstVal.UTF8)); | |
} | |
LOG.debug("模板:" + templateFilePath + "; 文件:" + outputFile); | |
} | |
} |
# 模板代码
在 resources 下面新建包名 templates,以下文件均放在此包下。
entity.java.ftl
package ${package.Entity}; | |
<#if superEntityClassPackage??> | |
import ${superEntityClassPackage}; | |
<#else> | |
import javax.persistence.Id; | |
</#if> | |
import io.swagger.annotations.ApiModel; | |
import javax.persistence.AttributeOverride; | |
import javax.persistence.AttributeOverrides; | |
import javax.persistence.Column; | |
import javax.persistence.Entity; | |
import javax.persistence.Table; | |
/** | |
* ${comment} 实体类 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
@Entity | |
@Table(schema = "${schema}", name = "${tableName}") | |
<#if superEntityClass??> | |
@AttributeOverrides({ | |
@AttributeOverride(name = "id", column = @Column(name = "${tablePrefix}_id", updatable = false, length = 40)) | |
}) | |
</#if> | |
@ApiModel(description = "${comment}") | |
<#if superEntityClass??> | |
public class ${table.entityName} extends ${superEntityClass} { | |
<#else> | |
public class ${table.entityName} { | |
@Id | |
private String id; | |
</#if> | |
} |
dao.java.ftl
package ${package.Dao}; | |
import org.springframework.stereotype.Repository; | |
import ${package.Entity}.${table.entityName}; | |
<#if superDaoClassPackage??> | |
import ${superDaoClassPackage}; | |
</#if> | |
/** | |
* ${comment} 数据仓库 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
<#if superDaoClass??> | |
@Repository | |
public interface ${table.daoName} extends ${superDaoClass}<${table.entityName}, String> { | |
<#else> | |
public interface ${table.daoName} { | |
</#if> | |
} |
daoImpl.java.ftl
package ${package.DaoImpl}; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import ${package.Entity}.${table.entityName}; | |
<#if superDaoImplClassPackage??> | |
import ${superDaoImplClassPackage}; | |
<#else> | |
import org.springframework.stereotype.Repository; | |
</#if> | |
/** | |
* ${comment} 数据仓库实现 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
<#if superDaoImplClass??> | |
public class ${table.daoImplName} extends ${superDaoImplClass}<${table.entityName}> { | |
private static final Logger LOG = LoggerFactory.getLogger(${table.daoImplName}.class); | |
public ${table.daoImplName}() { | |
super(${table.entityName}.class); | |
} | |
<#else> | |
@Repository | |
public class ${table.daoImplName} implements ${table.daoName}{ | |
</#if> | |
} |
service.java.ftl
package ${package.Service}; | |
import ${package.Entity}.${table.entityName}; | |
<#if superServiceClassPackage??> | |
import ${superServiceClassPackage}; | |
</#if> | |
/** | |
* ${comment} DAO 接口 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
<#if superEntityClass??> | |
public interface ${table.serviceName} extends ${superServiceClass}<${table.entityName}> { | |
<#else> | |
public interface ${table.serviceName} { | |
</#if> | |
} |
serviceImpl.java.ftl
package ${package.ServiceImpl}; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import ${package.Entity}.${table.entityName}; | |
import ${package.Dao}.${table.daoName}; | |
import ${package.Service}.${table.serviceName}; | |
<#if superServiceImplClassPackage??> | |
import ${superServiceImplClassPackage}; | |
</#if> | |
import org.springframework.beans.factory.annotation.Autowired; | |
import org.springframework.stereotype.Component; | |
/** | |
* ${comment} DAO 实现 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
<#if superServiceImplClass??> | |
@Component | |
public class ${table.serviceImplName} extends ${superServiceImplClass}<${table.entityName}> | |
implements ${table.serviceName} { | |
private static final Logger LOG = LoggerFactory.getLogger(${table.serviceImplName}.class); | |
@Autowired | |
private ${table.daoName} ${table.daoName?uncap_first}; | |
public ${table.serviceImplName}() { | |
super(${table.entityName}.class); | |
} | |
@Override | |
public ${table.daoName} getBaseDao() { | |
return ${table.daoName?uncap_first}; | |
} | |
<#else> | |
@Component | |
public class ${table.serviceImplName} implements ${table.serviceName}{ | |
private static final Logger LOG = LoggerFactory.getLogger(${table.serviceImplName}.class); | |
@Autowired | |
private ${table.daoName} ${table.daoName?uncap_first}; | |
</#if> | |
} |
controller.java.ftl
package ${package.Controller}; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import org.springframework.web.bind.annotation.RequestMapping; | |
import org.springframework.web.bind.annotation.RestController; | |
import ${package.Entity}.${table.entityName}; | |
import ${package.Service}.${table.serviceName}; | |
<#if superControllerClassPackage??> | |
import ${superControllerClassPackage}; | |
</#if> | |
import org.springframework.beans.factory.annotation.Autowired; | |
/** | |
* ${comment} DAO 实现 | |
* | |
* @author ${author} | |
* @date ${date} | |
*/ | |
<#if superControllerClass??> | |
@RestController | |
@RequestMapping(value = "/${tableName}") | |
public class ${table.controllerName} extends ${superControllerClass}<${table.entityName}>{ | |
private static final Logger LOG = LoggerFactory.getLogger(${table.controllerName}.class); | |
@Autowired | |
private ${table.serviceName} ${table.serviceName?uncap_first}; | |
@Override | |
public ${table.serviceName} getBaseService() { | |
return ${table.serviceName?uncap_first}; | |
} | |
<#else> | |
@RestController | |
@RequestMapping(value = "/${tableName}") | |
public class ${table.controllerName} { | |
private static final Logger LOG = LoggerFactory.getLogger(${table.controllerName}.class); | |
@Autowired | |
private ${table.serviceName} ${table.serviceName?uncap_first}; | |
</#if> | |
} |
# 自动生成类
放在包 com.qiyin.base.generator 下面。
AutoGenerator
package com.qiyin.base.generator; | |
import com.qiyin.base.generator.builder.ConfigBuilder; | |
import com.qiyin.base.generator.config.GlobalConfig; | |
import com.qiyin.base.generator.config.PackageConfig; | |
import com.qiyin.base.generator.config.TemplateConfig; | |
import com.qiyin.base.generator.dto.TableInfo; | |
import com.qiyin.base.generator.engine.AbstractTemplateEngine; | |
import com.qiyin.base.generator.engine.FreemarkerTemplateEngine; | |
import org.apache.commons.lang3.StringUtils; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import java.util.List; | |
/** | |
* 自动生成 | |
*/ | |
public class AutoGenerator { | |
private static final Logger LOG = LoggerFactory.getLogger(AutoGenerator.class); | |
/** | |
* 配置信息 | |
*/ | |
protected ConfigBuilder config; | |
/** | |
* 包 相关配置 | |
*/ | |
private PackageConfig packageInfo; | |
/** | |
* 模板 相关配置 | |
*/ | |
private TemplateConfig template; | |
/** | |
* 全局 相关配置 | |
*/ | |
private GlobalConfig globalConfig; | |
/** | |
* 模板引擎 | |
*/ | |
private AbstractTemplateEngine templateEngine; | |
public void execute(){ | |
LOG.info("=================准备生成文件...================="); | |
if (config == null){ | |
config = new ConfigBuilder(packageInfo, template, globalConfig); | |
} | |
if (templateEngine == null){ | |
// 默认采用 Velocity 引擎 | |
templateEngine = new FreemarkerTemplateEngine(); | |
} | |
// 模板引擎初始化执行文件输出 | |
templateEngine.init(pretreatmentConfigBuilder(config)).mkdirs().batchOutput(); | |
LOG.info("=================文件生成完成...================="); | |
} | |
/** | |
* 预处理配置 | |
* | |
* @param config 总配置信息 | |
* @return 解析数据结果集 | |
*/ | |
private ConfigBuilder pretreatmentConfigBuilder(ConfigBuilder config) { | |
// 表信息列表 | |
List<TableInfo> tables = getAllTableInfoList(config); | |
for (TableInfo table : tables){ | |
boolean importSerializable = true; | |
if (StringUtils.isNotBlank(config.getSuperEntityClass())) { | |
// 父实体 | |
table.setImportPackages(config.getSuperEntityClass()); | |
importSerializable = false; | |
} | |
} | |
return config.setTableInfoList(tables); | |
} | |
/** | |
* 开放表信息、预留子类重写 | |
* | |
* @param config 配置信息 | |
* @return ignore | |
*/ | |
protected List<TableInfo> getAllTableInfoList(ConfigBuilder config) { | |
return config.getTableInfoList(); | |
} | |
public AutoGenerator setPackageInfo(PackageConfig packageInfo) { | |
this.packageInfo = packageInfo; | |
return this; | |
} | |
public AutoGenerator setTemplate(TemplateConfig template) { | |
this.template = template; | |
return this; | |
} | |
public AutoGenerator setGlobalConfig(GlobalConfig globalConfig) { | |
this.globalConfig = globalConfig; | |
return this; | |
} | |
} |
Main
package com.qiyin.base.generator; | |
import com.qiyin.base.generator.config.ConstVal; | |
import com.qiyin.base.generator.config.GlobalConfig; | |
import com.qiyin.base.generator.config.PackageConfig; | |
import java.util.ArrayList; | |
import java.util.List; | |
public class Main { | |
public static void main(String[] args) { | |
List<Table> tables = new ArrayList<>(); | |
tables.add(new Table("goods", "Goods", "学生实体", "qiyin", "goods", "goods", "g")); | |
createTables(tables); | |
} | |
private static void createTables(List<Table> tables) { | |
tables.forEach(table -> | |
new AutoGenerator(). | |
setGlobalConfig( | |
new GlobalConfig() | |
// 作者 | |
.setAuthor(table.getAuthor()) | |
// 生成的代码在哪个模块里 | |
.setProject("business") | |
// 实体描述信息 | |
.setComment(table.getComment()) | |
// 实体名 | |
.setTableName(table.getName()) | |
// 生成类的样式 | |
.setClassType(ConstVal.MODEL_OTHER) | |
// 当前项目所在的文件目录 | |
.setOutputDir("D:\\code\\project") | |
// 表模式 | |
.setSchema(table.getSchema()) | |
// 数据表名 | |
.setDataTableName(table.getTableName()) | |
// 数据表字段前缀 | |
.setDataTablePrefix(table.getTablePrefix()) | |
) | |
.setPackageInfo(new PackageConfig().setPackageName(table.getModel())).execute()); | |
} | |
} | |
class Table { | |
public Table(String model, String name, String comment, String author, String schema, String tableName, String tablePrefix) { | |
this.model = model; | |
this.comment = comment; | |
this.name = name; | |
this.author = author; | |
this.schema = schema; | |
this.tableName = tableName; | |
this.tablePrefix = tablePrefix; | |
} | |
// 模块分包名 | |
private String model; | |
// 描述信息 | |
private String comment; | |
// 表名 | |
private String name; | |
// 作者 | |
private String author; | |
// 数据库模式 | |
private String schema; | |
// 数据库 | |
private String tableName; | |
// 字段前缀 | |
private String tablePrefix; | |
//get/set 省略 | |
} |
到此自动生成相关的实现已经结束。
# 扩展
在 base 模块下,新建 entity、dao、daoImpl、service、serviceImpl 和 controller 基类。
AbstactEntity
package com.qiyin.base.entity; | |
import io.swagger.annotations.ApiModel; | |
import io.swagger.annotations.ApiModelProperty; | |
import javax.persistence.Column; | |
import javax.persistence.Id; | |
import javax.persistence.MappedSuperclass; | |
import java.io.Serializable; | |
import java.time.LocalDate; | |
@MappedSuperclass | |
@ApiModel(value = "基类实体") | |
public abstract class AbstractEntity implements Serializable { | |
@ApiModelProperty(value = "主键") | |
@Id | |
private String id; | |
@ApiModelProperty(value = "创建时间") | |
@Column(name = "insert") | |
private LocalDate insert; | |
@ApiModelProperty(value = "数据状态") | |
@Column(name = "status") | |
private String status; | |
//get/set 省略... | |
} |
AbstractDao
package com.qiyin.base.dao; | |
import org.springframework.data.jpa.repository.JpaRepository; | |
import org.springframework.data.jpa.repository.JpaSpecificationExecutor; | |
import java.util.List; | |
/** | |
* 抽象实体数据层 | |
* | |
* @param <T> 实体 | |
* @param <ID> | |
*/ | |
public interface AbstractDao<T, ID> extends JpaRepository<T, ID>, JpaSpecificationExecutor<T> { | |
List<T> queryAll(); | |
} |
AbstractDaoImpl
package com.qiyin.base.dao; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import javax.persistence.EntityManager; | |
import javax.persistence.PersistenceContext; | |
import javax.persistence.criteria.CriteriaBuilder; | |
import javax.persistence.criteria.CriteriaQuery; | |
import javax.persistence.criteria.Root; | |
import java.util.List; | |
/** | |
* 抽象实体数据实现层 | |
* | |
* @param <T> 实体 | |
*/ | |
public abstract class AbstractDaoImpl<T>{ | |
protected static final Logger LOG = LoggerFactory.getLogger(AbstractDaoImpl.class); | |
@PersistenceContext | |
protected EntityManager em; | |
protected Class<T> entityClass; | |
public AbstractDaoImpl(Class<T> entityClass) { | |
this.entityClass = entityClass; | |
} | |
/** | |
* 查询所有实体数据. | |
* | |
* @return 实体列表 | |
*/ | |
public List<T> queryAll() { | |
CriteriaBuilder builder = this.em.getCriteriaBuilder(); | |
CriteriaQuery<T> query = builder.createQuery(entityClass); | |
Root<T> root = query.from(entityClass); | |
query.select(root); | |
return em.createQuery(query).getResultList(); | |
} | |
} |
AbstractService
package com.qiyin.base.service; | |
import com.qiyin.base.entity.AbstractEntity; | |
import java.util.List; | |
/** | |
* 抽象实体服务层 | |
* | |
* @param <T> 实体类 | |
*/ | |
public interface AbstractService<T extends AbstractEntity> { | |
List<T> queryAll(); | |
} |
AbstractServiceImpl
package com.qiyin.base.service; | |
import com.qiyin.base.dao.AbstractDao; | |
import com.qiyin.base.entity.AbstractEntity; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import java.util.List; | |
/** | |
* 抽象实体服务实现层 | |
*/ | |
public abstract class AbstractServiceImpl<T extends AbstractEntity> implements AbstractService<T>{ | |
private static final Logger LOG = LoggerFactory.getLogger(AbstractServiceImpl.class); | |
/** | |
* 主实体类. | |
*/ | |
protected Class<T> entityClass; | |
public AbstractServiceImpl(Class<T> entityClass) { | |
this.entityClass = entityClass; | |
} | |
/** | |
* 获取实体数据层对象. | |
* | |
* @return 实体数据层对象 | |
*/ | |
protected abstract AbstractDao<T, String> getBaseDao(); | |
@Override | |
public List<T> queryAll() { | |
return this.getBaseDao().queryAll(); | |
} | |
} |
AbstractController
package com.qiyin.base.controller; | |
import com.qiyin.base.entity.AbstractEntity; | |
import com.qiyin.base.service.AbstractService; | |
import io.swagger.annotations.ApiOperation; | |
import org.slf4j.Logger; | |
import org.slf4j.LoggerFactory; | |
import org.springframework.web.bind.annotation.GetMapping; | |
import java.util.List; | |
/** | |
* 抽象 REST 服务层 | |
*/ | |
public abstract class AbstractController<T extends AbstractEntity> { | |
private static final Logger LOG = LoggerFactory.getLogger(AbstractController.class); | |
/** | |
* 获取抽象业务接口. | |
* | |
* @return 抽象业务接口 | |
*/ | |
public abstract AbstractService<T> getBaseService(); | |
@ApiOperation(value = "获取所有实体数据") | |
@GetMapping(value = "/queryAll") | |
public List<T> queryAll() { | |
return this.getBaseService().queryAll(); | |
} | |
} |
将 Main 类中的 setClassType,设置为 MODEL_NORMAL,即可将所有自动生成的类继承至基类。
# 测试
在 PostgreSQL 数据库中新建 goods 模式,在此模式下新建数据表 goods,字段任意。(也可以使用这篇文章自动生成建表 SQL,根据实体自动生成建表 SQL 语句。)
启动 main 方法,将会在 business 模块下的四个子模块分别生成对应的代码。
可以新建一个启动模块用来启动 business 模块中的项目,也可以直接在 controller 层下的新建一个 MainApplication 启动类。
package com.example.business;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.domain.EntityScan;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
@EntityScan({
"com.example.business.entity"
})
@EnableJpaRepositories({
"com.example.business.dao"
})
@ComponentScan({
"com.example.business.dao",
"com.example.business.service",
"com.example.business.controller"
})
@SpringBootApplication
public class MainApplication {
public static void main(String[] args) {
SpringApplication.run(MainApplication.class, args);
}
}
在对应的启动类下面的 resources 里面新建 application.yml 文件。
spring:
datasource:
driver-class-name: org.postgresql.Driver
url: jdbc:postgresql://localhost:5432/test
username: postgres
password: 123456
server:
port: 8080
启动 MainApplication
如果生成的类样式设置的是 MODEL_OTHER,则需要手动在生成的代码中编写对应的接口以及实现,在浏览器中输入 http://localhost:8888/goods/ 接口名,出现与自己所写的结果一致,即成功!
如果生成的类样式设置的是 MODEL_NORMAL,在浏览器中输入 http://localhost:8888/goods/queryAll,出现数据即成功!