文章目录
前言
提示:
本篇使用方式为直接获取.java文件。上篇为.class文件。
本篇生成的sql包含,表字段备注;且对一组特殊命名的字段name进行项目的数据库字段type划分。
提示:以下是本篇文章正文内容,下面案例可供参考
使用步骤
一、代码如下
测下示例为一个实体类输出对应的mysql建表sql,代码如下:
package cn.iocoder.hw.module.erp.controller.test;
import cn.iocoder.hw.module.erp.dal.dataobject.finance.*;
import java.io.*;
import java.lang.invoke.SerializedLambda;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.math.BigDecimal;
import java.util.*;
import java.util.function.Function;
/**
* 根据实体类生成mysql表CREATE语句,包含表字段备注
* <p>
* 根据文件.java转换
*/
public class TableClassGeneratedTest {
// 一个实体类输出对应的mysql建表sql
public static void main(String[] args) throws Exception {
Table table = getTable(ErpAccountDO.class);
System.out.println(table.sql());
}
/**
* Java类转化为数据库表对象
*
* @param c java实体类
* @param <T> 泛型
* @return 数据库表对象
*/
private static <T> Table getTable(Class<T> c) {
List<String> codes = getClassSourceCodes(c);
Map<String, Column> columnMap = getFieldColumnMap(c, codes);
Class<? super T> superclass = c.getSuperclass();
if (Objects.nonNull(superclass)) {
if (superclass != Object.class) {
List<String> sourceCodes = getClassSourceCodes(c);
Map<String, Column> superColumnMap = getFieldColumnMap(superclass, sourceCodes);
columnMap.putAll(superColumnMap);
}
}
if (columnMap.isEmpty()) {
return null;
}
// 获取主键(如果包含名为 id 的属性,则以 id 为主键,否则,则取类中第一个属性为主键)
Column key;
if (columnMap.containsKey("id")) {
key = columnMap.get("id");
} else {
key = columnMap.entrySet().stream().findFirst().get().getValue();
}
// 剩下的则是其他属性
LinkedList<Column> columns = new LinkedList<>(columnMap.values());
if (!columns.get(0).getName().equals(key.getName())) {
Column copyKey = key.copy();
columns.remove(key);
columns.addFirst(copyKey);
}
Table table = new Table();
table.setName(getSqlName(c.getSimpleName()));
table.setComment(getTableComment(codes));
table.setColumns(columns);
return table;
}
private static <T> Map<String, Column> getFieldColumnMap(Class<T> c, List<String> codes) {
Map<String, String> fieldCommentMap = getClassFieldComment(codes, c.getSimpleName());
Field[] fields = c.getDeclaredFields();
Map<String, Column> columnMap = new LinkedHashMap<>();
for (Field field : fields) {
if (!Modifier.isStatic(field.getModifiers())) {
String fieldName = field.getName();
String columnName = getSqlName(fieldName);
Column column = new Column();
column.setName(columnName);
column.setType(getSqlType(field));
column.setComment(fieldCommentMap.get(fieldName));
columnMap.put(fieldName, column);
}
}
return columnMap;
}
/**
* 获取 mysql 数据类型
*
* @param field java 属性
* @return mysql的
*/
private static String getSqlType(Field field) {
Class<?> type = field.getType();
String name = getSqlName(field.getName());
if (type == String.class) {
return "varchar(255)";
} else if (type == int.class || type == Integer.class) {
if (Constant.TINYINT_WORDS.contains(name)) {
return "tinyint(4)";
}
if (name.startsWith("is_") || name.endsWith("_type") || name.endsWith("_status")) {
return "tinyint(4)";
}
return "int(11)";
} else if (type == long.class || type == Long.class) {
return "bigint(20)";
} else if (type == Float.class || type == float.class) {
return "float";
} else if (type == double.class || type == Double.class) {
// 最大为 (53, 15)
return "double(20,2)";
} else if (type == boolean.class || type == Boolean.class) {
return "boolean";
} else if (type == java.util.Date.class ||
type == java.sql.Date.clas