Напишите инструмент Java для создания классов сущностей из базы данных.
Заметки перед тем, как начать писать
Это всего лишь простой инструмент для создания java-файла в соответствии с результатом синтаксического анализа после анализа оператора построения таблицы базы данных. Это написано по двум причинам.
1: Никто в проекте не пишет аннотации классов сущностей, аннотации полей, и существующие инструменты не могут автоматически добавлять их в файлы классов на основе аннотаций базы данных.
2: Кажется, не так сложно написать его самостоятельно.
Поэтому я написал один сам.
Вот что используется при создании файла javafreemarker. использовалjdbcВ качестве инструмента для выполнения sql.
Этот проект выложен на github, адрес:GitHub.com/Хуан Цзяньсян60149632….
Используемые зависимости:
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
<dependency>
<groupId>org.freemarker</groupId>
<artifactId>freemarker</artifactId>
<version>2.3.28</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.45</version>
</dependency>
<dependency>
<groupId>com.mchange</groupId>
<artifactId>c3p0</artifactId>
<version>0.9.5.2</version>
</dependency>
Получить все имена таблиц в базе данных
Если вы хотите создать java-файл в соответствии с оператором построения таблиц в базе данных, вы должны сначала узнать, какие таблицы находятся в базе данных. Итак, начните.
Информация о настройке базы данных
Прежде чем получить ссылку на базу данных, мы сначала пишем файл для сохранения различной информации о ссылке на базу данных.
создать новый файлconfig.xml
<xml>
<jdbc.url></jdbc.url>
<jdbc.username></jdbc.username>
<jdbc.password></jdbc.password>
</xml>
jdbc.url: URL базы данных ссылок. Например: jdbc:mysql://127.0.0.1:3306/demo?useSSL=true
jdbc.username: Имя пользователя для базы данных.
jdbc.password: пароль для базы данных.
Это настроено.
Напишите класс инструмента для чтения xml: XmlUtils.java
import org.w3c.dom.Document;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.util.Scanner;
/**
* 读取xml
*/
public class XmlUtils {
/**
* 读取 Document
*
* @param xmlPath
* @return
*/
public static Document getConfigDocument(String xmlPath) {
try {
InputStream resourceAsStream = Thread.currentThread().getContextClassLoader().getResourceAsStream(xmlPath);
Scanner scanner = new Scanner(resourceAsStream);
StringBuilder stringBuilder = new StringBuilder();
while (scanner.hasNextLine()) {
stringBuilder.append(scanner.nextLine()).append("\n");
}
DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder documentBuilde = documentBuilderFactory.newDocumentBuilder();
Document document = documentBuilde.parse(new ByteArrayInputStream(stringBuilder.toString().getBytes()));
return document;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
}
Открыть ссылку на базу данных
//获取数据库配置信息
Document configXml = XmlUtils.getConfigDocument(CONFIG_PATH);
Element element = configXml.getDocumentElement();
String jdbcUrl = element.getElementsByTagName("jdbc.url").item(0).getTextContent();
String username = element.getElementsByTagName("jdbc.username").item(0).getTextContent();
String password = element.getElementsByTagName("jdbc.password").item(0).getTextContent();
//打开数据库链接
Connection conn = (Connection) DriverManager.getConnection(jdbcUrl, username, password);
После получения ссылки следующим шагом будет чтение данных таблицы в базе данных.
получить таблицу в базе данных
Statement statement = connection.createStatement();
ResultSet resultSet = statement.executeQuery("SHOW TABLES;");
while (resultSet.next()) {
//这里就获取到了数据库中的所有的表的名称了。
String tableName = resultSet.getString(1);
}
Получив здесь имя таблицы, вы можете, в свою очередь, получить оператор построения таблицы и проанализировать оператор построения таблицы.
Причина, по которой здесь используется метод разбора оператора построения таблицы, заключается в том, что аннотационная информация может быть получена более полно. При использовании другого метода аннотации таблицы не могут быть получены все время (забыл сказать о другом методе~).
получить инструкцию сборки
Вот сращивание sql, а потом его выполнить. Вот код:
Statement statement = connection.createStatement();
ResultSet resultSet = statement.executeQuery("show CREATE TABLE 表名称");
while (resultSet.next()) {
//这里就得到了表的建表语句
String createTableSql = resultSet.getString(2);
}
После этого шага мы полностью получили все операторы построения таблиц в базе данных. Следующим шагом является анализ оператора создания таблицы и его использование для создания классов сущностей.
Создать анализ оператора таблицы
создать таблицу sql
Ниже приведено выполнение sqlshow create table userрезультат:
CREATE TABLE `user` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '用户id',
`name` varchar(225) DEFAULT NULL COMMENT '用户名',
`create_date` datetime DEFAULT NULL,
`status` int(11) DEFAULT NULL,
`age` int(11) DEFAULT NULL COMMENT '年龄',
`mark` varchar(225) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2104778081 DEFAULT CHARSET=latin1 COMMENT='用户表'
Здесь видно, что имя создаваемого класса сущностей находится в первой строкеCREATE TABLEВ середине два последних символа **`**, чтобы мы могли вынести имя таблицы через регулярные выражения, а затем преобразовать его в нужное нам имя класса. Во-первых, давайте напишем метод для извлечения данных с помощью регуляризации, Ниже приведен код:
обычный код
/**
* 根据正则查找
*
* @param sql
* @param pattern
* @param group
* @return
*/
static String getByPattern(String sql, String pattern, int group) {
Pattern compile = Pattern.compile(pattern);
Matcher matcher = compile.matcher(sql);
while (matcher.find()) {
return matcher.group(group);
}
return null;
}
Теперь начните извлекать имя таблицы из оператора создания таблицы (хотя я уже знаю это, когда получаю все таблицы в базе данных, но нет проблем написать его один раз, правильно~~~), следующее код:
Получить имя таблицы
/**
* 获得表的名称
*
* @param sql
* @return
*/
public static String getTableName(String sql) {
return getByPattern(sql, "CREATE TABLE `(.*)`", 1);
}
Здесь имя таблицы было вынесено. Следующим шагом будет получение комментариев к таблице, здесь мы получаем комментарии к таблице. Вот код:
Извлечь комментарии к таблице
public static String getTableComment(String sql) {
return getByPattern(sql, "\\) .* COMMENT='(.*)'", 1);
}
Теперь начните получать информацию об идентификаторе.
получить идентификатор
Для получения id по-прежнему хорошо использовать обычный код, код выглядит следующим образом:
public static String getId(String sql) {
return getByPattern(sql, "PRIMARY KEY \\(`(.*)`\\)", 1);
}
Поскольку в исходном выражении есть пара круглых скобок, внешние круглые скобки здесь экранируются. Затем начните извлекать поля, типы полей и комментарии к полям в базе данных.
поле, тип поля, комментарий к полю
Сначала выньте SQL, связанный с полем в операторе построения таблицы.
21 января 2019 г., изменено:
Неожиданно в некоторых таблицах отсутствует id, что приводит к ошибке после выполнения следующего кода Изменить решение конца.
/**
* 获取建表语句中和字段相关的sql
*
* @param sql
* @return
*/
public static List<String> getColumnSqls(String sql) {
List<String> lines = new ArrayList<>();
Scanner scanner = new Scanner(sql);
boolean start = false;
while (scanner.hasNextLine()) {
String nextLine = scanner.nextLine();
if (nextLine.indexOf("CREATE TABLE") != -1) {
start = true;
continue;
}
//没想到有的表没有id /(ㄒoㄒ)/~~
if (nextLine.indexOf("PRIMARY KEY") != -1 || nextLine.indexOf("ENGINE=") != -1) {
start = false;
continue;
}
if (start) {
lines.add(nextLine);
}
}
return lines;
}
Результат работы здесь:
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '用户id',
`name` varchar(225) DEFAULT NULL COMMENT '用户名',
`create_date` datetime DEFAULT NULL,
`status` int(11) DEFAULT NULL,
`age` int(11) DEFAULT NULL COMMENT '年龄',
`mark` varchar(225) DEFAULT NULL,
Это также получает всю информацию, связанную с полем в таблице.Далее, давайте получим имя поля:
Получить имена столбцов, комментарии, типы данных
List<String> columns = SqlUtils.getColumnSqls(sql);
for (String oneLine : columns) {
System.out.println(oneLine);
String columnName = SqlUtils.getByPattern(oneLine, "`(.*)`", 1);
String comment = SqlUtils.getByPattern(oneLine, "COMMENT '(.*)'", 1);
String columnType = SqlUtils.getByPattern(oneLine, "`" + columnName + "` ([A-Za-z]*)", 1);
System.out.printf("名称:%-20s 类型:%-20s 注释:%-20s \n", columnName, columnType, comment);
}
Выходной результат:
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '用户id',
名称:id 类型:int 注释:用户id
`name` varchar(225) DEFAULT NULL COMMENT '用户名',
名称:name 类型:varchar 注释:用户名
`create_date` datetime DEFAULT NULL,
名称:create_date 类型:datetime 注释:null
`status` int(11) DEFAULT NULL,
名称:status 类型:int 注释:null
`age` int(11) DEFAULT NULL COMMENT '年龄',
名称:age 类型:int 注释:年龄
`mark` varchar(225) DEFAULT NULL,
名称:mark 类型:varchar 注释:null
На данный момент я получил все необходимые данные из оператора построения таблицы и начну использовать эти данные для создания java-файлов.
Начните создавать java-файлы на основе данных, полученных выше.
Наконец начал создавать java файлы.
Но ~ при создании java файла нужно сначала обработать данные, полученные ранее, и преобразовать формат в sql в формат в java. Например, имена атрибутов, типы данных, имена классов и т. д., начните сейчас~
Преобразование имен таблиц в соответствующие имена классов
Это соглашение об именах с заглавной буквы в верблюжьем регистре. Например, будетuser_logилиUSER_LOGКонвертировать в UserLog.
Мы можем написать:
/**
* 类名称转换
*
* @param tableName
* @return
*/
public static String entityName(String tableName) {
String lowerCaseName = tableName.toLowerCase();
StringBuilder newName = new StringBuilder();
char[] chars = lowerCaseName.toCharArray();
boolean change = false;
for (int i = 0; i < chars.length; i++) {
char aChar = chars[i];
if (aChar == '_' && !change) {
change = true;
continue;
}
//首字母大写
if (i == 0) {
aChar = Character.toUpperCase(aChar);
}
if (change) {
aChar = Character.toUpperCase(aChar);
change = false;
}
newName.append(aChar);
}
return newName.toString();
}
Это дает имя класса, который нам нужен.
Преобразование имени поля в имя свойства в java
Вот, чтобы удалить заглавную букву предыдущей операции.Ниже приведен код:
/**
* 属性名称转换
*
* @param name
* @return
*/
public static String fieldName(String name) {
name = name.toLowerCase();
StringBuilder newName = new StringBuilder();
char[] chars = name.toCharArray();
boolean change = false;
for (int i = 0; i < chars.length; i++) {
char aChar = chars[i];
if (aChar == '_' && !change) {
change = true;
continue;
}
if (change) {
aChar = Character.toUpperCase(aChar);
change = false;
}
newName.append(aChar);
}
return newName.toString();
}
Следующим шагом является преобразование типа данных в sql в тип данных в java.
преобразование типа данных sql
Здесь карта используется для создания отображения, и вы можете изменить ее самостоятельно, если у вас есть свои особые требования.
public class ColumnFieldTypeMapping {
private Map<String, Class> sqlFieldTypeMapping = new HashMap<>();
{
sqlFieldTypeMapping.put("VARCHAR", String.class);
sqlFieldTypeMapping.put("CHAR", String.class);
sqlFieldTypeMapping.put("TEXT", String.class);
sqlFieldTypeMapping.put("MEDIUMTEXT", String.class);
sqlFieldTypeMapping.put("LONGTEXT", String.class);
sqlFieldTypeMapping.put("TINYTEXT", String.class);
sqlFieldTypeMapping.put("BIT", Boolean.class);
sqlFieldTypeMapping.put("INT", int.class);
sqlFieldTypeMapping.put("BIGINT", long.class);
sqlFieldTypeMapping.put("DOUBLE", double.class);
sqlFieldTypeMapping.put("TINYINT", int.class);
sqlFieldTypeMapping.put("FLOAT", float.class);
sqlFieldTypeMapping.put("DECIMAL", BigDecimal.class);
sqlFieldTypeMapping.put("INT UNSIGNED", int.class);
sqlFieldTypeMapping.put("BIGINT UNSIGNED", int.class);
sqlFieldTypeMapping.put("DECIMAL UNSIGNED", BigDecimal.class);
sqlFieldTypeMapping.put("DATETIME", Date.class);
sqlFieldTypeMapping.put("TIME", Date.class);
sqlFieldTypeMapping.put("DATE", Date.class);
sqlFieldTypeMapping.put("TIMESTAMP", Date.class);
}
/**
* 根据sql数据类型获取Java数据类型
*
* @param columnType
* @return
*/
public Class getFieldType(String columnType) {
Class aClass = sqlFieldTypeMapping.get(columnType);
if (aClass == null) {
return sqlFieldTypeMapping.get(columnType.toUpperCase());
}
return null;
}
}
На данный момент вся информация, необходимая для создания java-файла, получена.
На данный момент нам нужно собрать их и поместить в freemarker, чтобы проанализировать и сгенерировать содержимое в java-файле.
Параметры сборки
Здесь, возможно, я буду использовать этот код для других целей в будущем, поэтому я создал два класса, один из которыхClassModel.java,одинEntityModel.java.
EntityModel наследует ClassModel. Мы в основном используемEntityModel.java. Вот код:
import java.util.*;
/**
* 用于生成java Entity文件的类
*/
public class ClassModel {
/**
* java 中不需要引包的类型
*/
private static List<Class> baseClass = Arrays.asList(
int.class,
double.class,
float.class,
long.class,
short.class,
byte.class,
char.class,
boolean.class,
String.class
);
/**
* 类注释
*/
private String classDoc;
/**
* 类名
*/
private String className;
/**
* 类 包名
*/
private String packageName;
/**
* K:属性名称
* V:属性类型
*/
private Map<String, Class> fields = new HashMap<>();
/**
* 属性的注释
*/
private Map<String, String> fieldDoc = new HashMap<>();
;
private List<Class> imports = new ArrayList<>();
/**
* 添加需要导入的包
*
* @param importClass
*/
public void addImport(Class importClass) {
if (baseClass.indexOf(importClass) != -1) {
return;
}
if (imports.indexOf(importClass) == -1) {
imports.add(importClass);
}
}
/**
* 添加属性
*
* @param fieldName 属性名称
* @param fieldClass 属性类型
*/
public void addfield(String fieldName, Class fieldClass) {
if (!fields.containsKey(fieldName)) {
fields.put(fieldName, fieldClass);
}
}
/**
* 添加属性注释
*
* @param fieldName 属性名称
* @param fieldDoc 属性注释
*/
public void addfieldDoc(String fieldName, String fieldDoc) {
if (!this.fieldDoc.containsKey(fieldName)) {
this.fieldDoc.put(fieldName, fieldDoc);
}
}
public List<Class> getImports() {
return imports;
}
public void setImports(List<Class> imports) {
this.imports = imports;
}
public String getClassDoc() {
return classDoc;
}
public void setClassDoc(String classDoc) {
this.classDoc = classDoc;
}
public String getClassName() {
return className;
}
public void setClassName(String className) {
this.className = className;
}
public String getPackageName() {
return packageName;
}
public void setPackageName(String packageName) {
this.packageName = packageName;
}
public Map<String, Class> getFields() {
return fields;
}
public void setFields(Map<String, Class> fields) {
this.fields = fields;
}
public Map<String, String> getFieldDoc() {
return fieldDoc;
}
public void setFieldDoc(Map<String, String> fieldDoc) {
this.fieldDoc = fieldDoc;
}
@Override
public String toString() {
final StringBuilder sb = new StringBuilder("{");
sb.append(" \"classDoc\"=\"").append(classDoc).append('\"');
sb.append(", \"className\"=\"").append(className).append('\"');
sb.append(", \"packageName\"=\"").append(packageName).append('\"');
sb.append(", \"fields\"=").append(fields);
sb.append(", \"fieldDoc\"=").append(fieldDoc);
sb.append(", \"imports\"=").append(imports);
sb.append('}');
return sb.toString();
}
}
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* 数据库映射
*/
public class EntityModel extends ClassModel {
/**
* 数据库名称
*/
private String tableName;
/**
* 数据库中的Id字段名称
*/
private List<String> idColumnNames = new ArrayList<>();
/**
* 类属性名对应数据库字段映射
* key: class 属性名称
* value:数据库字段名
*/
private Map<String, String> fieldSqlName = new HashMap<>();
/**
* 添加class 属性映射和 数据库 字段映射
*
* @param fieldName
* @param sqlName
*/
public void addfieldSqlName(String fieldName, String sqlName) {
if (!fieldSqlName.containsKey(fieldName)) {
fieldSqlName.put(fieldName, sqlName);
}
}
/**
* 添加id字段名
*
* @param idColumnName
*/
public void addIdColumnName(String idColumnName) {
idColumnNames.add(idColumnName);
}
public String getTableName() {
return tableName;
}
public void setTableName(String tableName) {
this.tableName = tableName;
}
public Map<String, String> getFieldSqlName() {
return fieldSqlName;
}
public void setFieldSqlName(Map<String, String> fieldSqlName) {
this.fieldSqlName = fieldSqlName;
}
public List<String> getIdColumnNames() {
return idColumnNames;
}
public void setIdColumnNames(List<String> idColumnNames) {
this.idColumnNames = idColumnNames;
}
}
Здесь собираются данные, полученные из базы данных, и с помощью freemarker можно сгенерировать содержимое файла Java. Вот код:
/**
* 根据建表语句组装EntityModel
*
* @param createTableSql
* @return
*/
EntityModel makeModelBySql(String createTableSql) {
Formatter formatter = new Formatter();
EntityModel model = new EntityModel();
String tableComment = SqlUtils.getTableComment(createTableSql);
String tableName = SqlUtils.getTableName(createTableSql);
String id = SqlUtils.getId(createTableSql);
model.addIdColumnName(id);
model.setClassName(NameConvert.entityName(tableName));
model.setTableName(tableName);
//注释是null的时候用数据库表名作为注释
model.setClassDoc(tableComment == null ? tableName : tableComment);
List<String> line = SqlUtils.getColumnSqls(createTableSql);
for (String oneLine : line) {
String columnName = SqlUtils.getByPattern(oneLine, "`(.*)`", 1);
String comment = SqlUtils.getByPattern(oneLine, "COMMENT '(.*)'", 1);
String columnType = SqlUtils.getByPattern(oneLine, "`" + columnName + "` ([A-Za-z]*)", 1);
String fieldName = NameConvert.fieldName(columnName);
Class fieldClass = columnFieldTypeMapping.getFieldType(columnType);
if (fieldClass == null) {
formatter.format("table:%s columnName:%s sql类型:%s 没有映射类型", tableName, columnName, columnType);
throw new UnsupportedOperationException(formatter.toString());
}
model.addfield(fieldName, fieldClass);
//字段注释是null的时候用数据库字段名作为注释
model.addfieldDoc(fieldName, comment == null ? columnName : comment);
model.addfieldSqlName(fieldName, columnName);
model.addImport(fieldClass);
}
return model;
}
Такой параметр нам нужен собран. Теперь начните писать код для freemarker.
класс инструмента freemarker
Используется для загрузки шаблонов freemarker и параметров обработки в шаблонах.FreeMarkerUtils.java, код показан ниже:
import freemarker.cache.StringTemplateLoader;
import freemarker.template.Configuration;
import freemarker.template.DefaultObjectWrapper;
import freemarker.template.Template;
import java.io.StringWriter;
import java.io.Writer;
import java.util.Locale;
import java.util.Scanner;
public class FreeMarkerUtils {
/**
* freemarker工具,
*
* @param subjectParams
* @param templetPath
* @return
* @throws Exception
*/
public static String getJavaClass(Object subjectParams, String templetPath) throws Exception {
StringTemplateLoader loader = new StringTemplateLoader();
Scanner scanner = new Scanner(Thread.currentThread().getContextClassLoader().getResourceAsStream(templetPath));
StringBuilder builder = new StringBuilder();
while (scanner.hasNext()) {
builder.append(scanner.nextLine()).append("\n");
}
String name = System.currentTimeMillis() + "";
loader.putTemplate(name, builder.toString());
//第一步:实例化Freemarker的配置类
Configuration conf = new Configuration();
conf.setObjectWrapper(new DefaultObjectWrapper());
conf.setLocale(Locale.CHINA);
conf.setDefaultEncoding("utf-8");
conf.setTemplateLoader(loader);
//处理空值为空字符串
conf.setClassicCompatible(true);
Template template = conf.getTemplate(name);
Writer out = new StringWriter(2048);
template.process(subjectParams, out);
String javaClass = out.toString();
return javaClass;
}
}
Теперь, когда у нас есть класс инструмента, мы не можем сразу начать генерировать java-файлы, потому что нам нужно продолжать устанавливать java-пакет и путь к генерируемым файлам.В это время мы можем изменить ранее написанныйconfig.xml
Изменить config.xml
<xml>
<jdbc.url></jdbc.url>
<jdbc.username></jdbc.username>
<jdbc.password></jdbc.password>
<basePath>/home/hjx/work/demo/src/main/java</basePath>
<entityPackage>top.hejiaxuan.demo.entity</entityPackage>
</xml>
Здесь добавляются два параметра:basePathа такжеentityPackage. Один — это путь к файлу для создания java, а другой — имя пакета java-файла.
Затем мы пишем класс инструмента, который записывает файлFileUtils.java
Напишите FileUtils.java
import java.io.*;
public class FileUtils {
/**
* 写入文件
*
* @param path 文件路径
* @param content 文件内容
*/
public static void write(String path, String content) {
File file = new File(path);
File parentFile = file.getParentFile();
try {
if (!parentFile.exists()) {
parentFile.mkdirs();
}
if (!file.exists()) {
file.createNewFile();
}
FileWriter fileWriter = new FileWriter(file);
fileWriter.write(content);
fileWriter.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Таким образом, все готово, осталось только сгенерировать файл. Давайте начнем сейчас~~~
Начать генерацию java-файлов
Перед генерацией файла нам также нужно поставитьbasePath,entityPackageУберите его из конфигурационного файла, я не буду писать этот шаг~~
static final String DOT = ".";
static final String FILE_TYPE = ".java";
static final String ENTITY_TEMPLET_PATH = "EntityTemp.ftl";
/**
* 用于生成一个类文件
*
* @param entityModel
* @return
*/
boolean makeOneClass(EntityModel entityModel) {
entityModel.setPackageName(entityPackage);
String filePath = basePath + "/" + entityPackage.replace(DOT, "/") + "/" + entityModel.getClassName() + FILE_TYPE;
try {
String javaClassString = FreeMarkerUtils.getJavaClass(entityModel, ENTITY_TEMPLET_PATH);
FileUtils.write(filePath, javaClassString);
return true;
} catch (Exception e) {
e.printStackTrace();
}
return false;
}
Ладно~~~ Готово.
эм~~~
Кажется, чего-то не хватает
Файл шаблона не выпущен~~~
написатьEntityTemp.ftl
package ${packageName};
<#--导入的包-->
<#list imports as import>
import ${import.name};
</#list>
<#--类名-->
<#if classDoc?length gt 0>
/**
* ${classDoc}
* @author hejiaxuan
*/
</#if>
public class ${className} {
<#--属性名称-->
<#list fields?keys as key>
<#assign fieldDocStr = fieldDoc[key]>
<#if fieldDocStr?length gt 0>
/**${fieldDocStr}*/
</#if>
<#if idColumnNames?seq_contains(fieldSqlName[key])>
</#if>
private ${fields[key].simpleName} ${key};
</#list>
<#list fields?keys as key>
<#assign fieldClass = fields[key].simpleName>
<#--setter-->
public void set${key?cap_first}(${fieldClass} ${key}) {
this.${key} = ${key};
}
<#--getter-->
public ${fieldClass} <#if fieldClass="boolean">is<#else>get</#if>${key?cap_first}() {
return this.${key};
}
</#list>
@Override
public String toString() {
final StringBuilder sb = new StringBuilder("[");
<#list fields?keys as key>
sb.append("${key}:").append(${key}).append("; ");
</#list>
sb.append("]");
return sb.toString();
}
}
В конце концов
Здесь я просто разместил некоторые фрагменты кода для использования, а не писал все коды. По сути, написание инструментов — это процесс медленной реализации собственных идей, если есть идеи, то все очень просто.
Если кому-то нужен полный код проекта, пожалуйста, перейдите по ссылкеGitHub.com/Хуан Цзяньсян60149632…Убедитесь сами.
над
другие
Если вы считаете, что то, что я написал, нормально, пожалуйста, прочитайте другие статьи ^_^