You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

312 lines
8.8 KiB
Java

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

package com.ruoyi;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.collection.ListUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.io.resource.ResourceUtil;
import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.ClassUtil;
import cn.hutool.core.util.StrUtil;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.ruoyi.common.annotation.Info;
import lombok.Data;
import org.apache.velocity.VelocityContext;
import org.apache.velocity.app.VelocityEngine;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import org.springframework.data.annotation.Id;
import java.io.File;
import java.io.StringWriter;
import java.lang.reflect.Field;
import java.util.Arrays;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;
@Info
public class MongoGenerator {
/**
* 输出的类的根包扫描的实体类为该包下的mongo子包下
*/
private String packageName = "com.ruoyi.jobs";
/**
* 模块名,类的简单名称会先去掉前面的模块名
*/
private String moduleName = "jobs";
@Test
@Disabled
@DisplayName("mongodb代码生成")
public void generate() throws Exception {
List<BaseInfo> entityList = scan(); //所有编写了@Info的实体类
// List<BaseInfo> entityList = scan("JobsTag1");//编写了@Info的实体类中的某些类
System.out.println(new ObjectMapper().writerWithDefaultPrettyPrinter().writeValueAsString(entityList));
generate(entityList);
System.out.println("完成");
}
public void generate(List<BaseInfo> entityList) throws Exception {
File[] fs = getOutPath();
/**
* 工程根
*/
File root = fs[0];
/**
* java包根目录
*/
File javaRoot = fs[1];
for (BaseInfo entity : entityList) {
String code = generate("query.vm", entity, entityList);
new File(javaRoot, "mongo/query").mkdirs();
FileUtil.writeString(code, new File(javaRoot, "mongo/query/" + entity.toUpperName() + "Query.java"), "UTF-8");
code = generate("api.vm", entity, entityList);
new File(javaRoot, "api").mkdirs();
FileUtil.writeString(code, new File(javaRoot, "api/" + entity.toUpperName() + "Api.java"), "UTF-8");
code = generate("api.js.vm", entity, entityList);
new File(root, "admin-ui/src/views/" + moduleName + "/api").mkdirs();
FileUtil.writeString(code, new File(root, "admin-ui/src/views/" + moduleName + "/api/" + entity.toSimpleLowerName() + ".js"), "UTF-8");
code = generate("index.vue.vm", entity, entityList);
new File(root, "admin-ui/src/views/" + moduleName + "/" + entity.toSimpleLowerName()).mkdirs();
FileUtil.writeString(code, new File(root, "admin-ui/src/views/" + moduleName + "/" + entity.toSimpleLowerName() + "/index.vue"), "UTF-8");
code = generate("WAdd.vue.vm", entity, entityList);
new File(root, "admin-ui/src/views/" + moduleName + "/" + entity.toSimpleLowerName() + "/components").mkdirs();
FileUtil.writeString(code, new File(root, "admin-ui/src/views/" + moduleName + "/" + entity.toSimpleLowerName() + "/components/WAdd.vue"), "UTF-8");
code = generate("WEdit.vue.vm", entity, entityList);
FileUtil.writeString(code, new File(root, "admin-ui/src/views/" + moduleName + "/" + entity.toSimpleLowerName() + "/components/WEdit.vue"), "UTF-8");
}
String code = generate("sql.vm", null, entityList);
FileUtil.writeString(code, new File(root, moduleName + "-menu.sql"), "UTF-8");
}
/**
* 使用模板引擎生成代码
*
* @param template
* @param entity
* @param list
* @return
* @throws Exception
*/
public String generate(String template, BaseInfo entity, List<BaseInfo> list) throws Exception {
VelocityEngine ve = new VelocityEngine();
ve.init();
VelocityContext context = new VelocityContext();
context.put("package", packageName);
context.put("entity", entity);
context.put("list", list);
context.put("moduleName", moduleName);
StringWriter writer = new StringWriter();
template = ResourceUtil.readUtf8Str("classpath:/generator/" + template);
ve.evaluate(context, writer, this.getClass().getName(), template);
return writer.toString();
}
/**
* 获取输出的java包源目录
*
* @return
*/
public File[] getOutPath() {
Set<String> paths = ClassUtil.getClassPaths(packageName);
if (CollUtil.isEmpty(paths) || paths.size() != 1) {
throw new RuntimeException("不能确定java包源目录");
}
String path = paths.iterator().next();
File file = new File(path.replace("/target/classes/", "/src/main/java/"));
File root = new File(path.substring(0, path.indexOf("/target/classes/"))).getParentFile();
return new File[]{root, file};
}
/**
* 扫描获取包下需要生成的实体信息
*
* @param includes 包含的类名,不填表示扫描所有
* @return
*/
public List<BaseInfo> scan(String... includes) {
Info defaultInfo = MongoGenerator.class.getAnnotation(Info.class);
List<BaseInfo> entityList = ListUtil.list(true);
ClassUtil.scanPackageByAnnotation(packageName + ".mongo", Info.class).stream().filter(c -> {
if (ArrayUtil.isEmpty(includes)) {
return true;
} else {
return ArrayUtil.indexOf(includes, c.getSimpleName()) > -1;
}
}).forEach(entityClazz -> {
BaseInfo entityInfo = loadByInfo(entityClazz.getAnnotation(Info.class));
entityList.add(entityInfo);
entityInfo.setClazz(entityClazz);
entityInfo.setJavaName(entityClazz.getSimpleName());
entityInfo.setModuleName(moduleName);
entityInfo.all = Arrays.stream(entityClazz.getDeclaredFields()).map(field -> {
BaseInfo info = null;
if (field.isAnnotationPresent(Info.class)) {
info = loadByInfo(field.getAnnotation(Info.class));
} else {
info = loadByInfo(defaultInfo);
}
info.setClazz(field.getType());
info.setJavaName(field.getName());
info.setIsId(field.isAnnotationPresent(Id.class));
info.setModuleName(moduleName);
return info;
}).sorted((a, b) -> a.order - b.order).collect(Collectors.toList());
entityInfo.cols = entityInfo.all.stream().filter(a -> !a.isId).collect(Collectors.toList());
entityInfo.id = entityInfo.all.stream().filter(a -> a.isId).findFirst().get();
});
return entityList;
}
public BaseInfo loadByInfo(Info info) {
BaseInfo base = new BaseInfo();
base.setAdd(info.add());
base.setUpdate(info.update());
base.setShow(info.show());
base.setOrder(info.order());
base.setName(info.value());
if (!info.addDefault().equals("")) {
base.setAddDefault(info.addDefault());
}
if (!info.updateDefault().equals("")) {
base.setUpdateDefault(info.updateDefault());
}
if (!info.comment().equals("")) {
base.setComment(info.comment());
}
return base;
}
@Data
public static class BaseInfo {
public Class<?> clazz;
public Field field;
/**
* 所有字段
*/
public List<BaseInfo> all;
/**
* 不含主键
*/
public List<BaseInfo> cols;
/**
* 主键字段
*/
public BaseInfo id;
public Boolean isId = false;
public String name;
public String getName() {
if (StrUtil.isBlank(name)) {
return javaName;
} else {
return name;
}
}
public String javaName;
public String moduleName;
public String toUpperName() {
return javaName.substring(0, 1).toUpperCase() + javaName.substring(1);
}
/**
* 去掉模块名后的
*
* @return
*/
public String toSimpleUpperName() {
String n = toLowerName();
if (n.startsWith(moduleName)) {
return n.substring(moduleName.length());
} else {
return toUpperName();
}
}
public String toSimpleLowerName() {
String n = toLowerName();
if (n.startsWith(moduleName)) {
n = n.substring(moduleName.length());
return n.substring(0, 1).toLowerCase() + n.substring(1);
} else {
return toLowerName();
}
}
public String toLowerName() {
return javaName.substring(0, 1).toLowerCase() + javaName.substring(1);
}
public String comment;
/**
* @param tabNum
* @return
*/
public String toComment(int tabNum) {
if (tabNum < 0) {
tabNum = 0;
}
String tabs = tabNum > 0 ? String.format("%" + (tabNum * 2) + "s", "") + " * " : " * ";
if (StrUtil.isNotBlank(comment)) {
return tabs + comment.replace("\n", "\n" + tabs);
} else {
return tabs;
}
}
public boolean show;
public boolean add;
public String addDefault;
public boolean update;
public String updateDefault;
public int order;
}
}