Commit b34e2691f82023e0b1b43ec8014f715fb21a2f73

Authored by YunaiV
1 parent f1069aa3

支持主流数据库的代码生成

Showing 30 changed files with 270 additions and 1018 deletions
yudao-dependencies/pom.xml
@@ -25,6 +25,7 @@ @@ -25,6 +25,7 @@
25 <mysql.version>5.1.46</mysql.version> 25 <mysql.version>5.1.46</mysql.version>
26 <druid.version>1.2.8</druid.version> 26 <druid.version>1.2.8</druid.version>
27 <mybatis-plus.version>3.4.3.4</mybatis-plus.version> 27 <mybatis-plus.version>3.4.3.4</mybatis-plus.version>
  28 + <mybatis-plus-generator.version>3.5.2</mybatis-plus-generator.version>
28 <dynamic-datasource.version>3.5.0</dynamic-datasource.version> 29 <dynamic-datasource.version>3.5.0</dynamic-datasource.version>
29 <redisson.version>3.17.0</redisson.version> 30 <redisson.version>3.17.0</redisson.version>
30 <!-- Config 配置中心相关 --> 31 <!-- Config 配置中心相关 -->
@@ -195,6 +196,11 @@ @@ -195,6 +196,11 @@
195 </dependency> 196 </dependency>
196 <dependency> 197 <dependency>
197 <groupId>com.baomidou</groupId> 198 <groupId>com.baomidou</groupId>
  199 + <artifactId>mybatis-plus-generator</artifactId> <!-- 代码生成器,使用它解析表结构 -->
  200 + <version>${mybatis-plus-generator.version}</version>
  201 + </dependency>
  202 + <dependency>
  203 + <groupId>com.baomidou</groupId>
198 <artifactId>dynamic-datasource-spring-boot-starter</artifactId> <!-- 多数据源 --> 204 <artifactId>dynamic-datasource-spring-boot-starter</artifactId> <!-- 多数据源 -->
199 <version>${dynamic-datasource.version}</version> 205 <version>${dynamic-datasource.version}</version>
200 </dependency> 206 </dependency>
yudao-framework/yudao-spring-boot-starter-mybatis/src/main/java/cn/iocoder/yudao/framework/mybatis/core/util/JdbcUtils.java
1 package cn.iocoder.yudao.framework.mybatis.core.util; 1 package cn.iocoder.yudao.framework.mybatis.core.util;
2 2
3 -import com.baomidou.mybatisplus.annotation.DbType;  
4 -import lombok.SneakyThrows;  
5 -import org.springframework.dao.DataAccessException;  
6 -import org.springframework.jdbc.core.JdbcTemplate;  
7 -import org.springframework.jdbc.core.RowCallbackHandler;  
8 -import org.springframework.jdbc.core.RowMapper;  
9 -  
10 -import java.sql.*;  
11 -import java.util.ArrayList;  
12 -import java.util.List; 3 +import java.sql.Connection;
  4 +import java.sql.DriverManager;
13 5
14 /** 6 /**
15 * JDBC 工具类 7 * JDBC 工具类
@@ -34,52 +26,4 @@ public class JdbcUtils { @@ -34,52 +26,4 @@ public class JdbcUtils {
34 } 26 }
35 } 27 }
36 28
37 - /**  
38 - * 获得连接  
39 - *  
40 - * @param url 数据源连接  
41 - * @param username 账号  
42 - * @param password 密码  
43 - * @return 是否正确  
44 - */  
45 - @SneakyThrows  
46 - public static Connection getConnection(String url, String username, String password) {  
47 - return DriverManager.getConnection(url, username, password);  
48 - }  
49 -  
50 - /**  
51 - * 执行指定 SQL,返回查询列表  
52 - *  
53 - * 参考 {@link JdbcTemplate#query(String, RowMapper)} 实现,主要考虑 JdbcTemplate 不支持使用指定 Connection 查询  
54 - *  
55 - * @param connection 数据库连接  
56 - * @param sql SQL  
57 - * @param handler 行处理器  
58 - * @return 列表  
59 - */  
60 - @SneakyThrows  
61 - public static <T> List<T> query(Connection connection, String sql, RowMapper<T> handler) {  
62 - try (PreparedStatement ps = connection.prepareStatement(sql);  
63 - ResultSet rs = ps.executeQuery()) {  
64 - // 处理结果  
65 - List<T> result = new ArrayList<>();  
66 - int rowNum = 0;  
67 - while (rs.next()) {  
68 - result.add(handler.mapRow(rs, rowNum++));  
69 - }  
70 - return result;  
71 - }  
72 - }  
73 -  
74 - /**  
75 - * 获得 URL 对应的 DB 类型  
76 - *  
77 - * @param url URL  
78 - * @return DB 类型  
79 - */  
80 - public static DbType getDbType(String url) {  
81 - String name = com.alibaba.druid.util.JdbcUtils.getDbType(url, null);  
82 - return DbType.getDbType(name);  
83 - }  
84 -  
85 } 29 }
yudao-module-infra/yudao-module-infra-biz/pom.xml
@@ -47,6 +47,10 @@ @@ -47,6 +47,10 @@
47 <groupId>cn.iocoder.boot</groupId> 47 <groupId>cn.iocoder.boot</groupId>
48 <artifactId>yudao-spring-boot-starter-mybatis</artifactId> 48 <artifactId>yudao-spring-boot-starter-mybatis</artifactId>
49 </dependency> 49 </dependency>
  50 + <dependency>
  51 + <groupId>com.baomidou</groupId>
  52 + <artifactId>mybatis-plus-generator</artifactId> <!-- 代码生成器,使用它解析表结构 -->
  53 + </dependency>
50 54
51 <dependency> 55 <dependency>
52 <groupId>cn.iocoder.boot</groupId> 56 <groupId>cn.iocoder.boot</groupId>
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/CodegenController.java
@@ -4,19 +4,18 @@ import cn.hutool.core.io.IoUtil; @@ -4,19 +4,18 @@ import cn.hutool.core.io.IoUtil;
4 import cn.hutool.core.util.ZipUtil; 4 import cn.hutool.core.util.ZipUtil;
5 import cn.iocoder.yudao.framework.common.pojo.CommonResult; 5 import cn.iocoder.yudao.framework.common.pojo.CommonResult;
6 import cn.iocoder.yudao.framework.common.pojo.PageResult; 6 import cn.iocoder.yudao.framework.common.pojo.PageResult;
  7 +import cn.iocoder.yudao.framework.common.util.servlet.ServletUtils;
  8 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenCreateListReqVO;
7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenDetailRespVO; 9 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenDetailRespVO;
8 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenPreviewRespVO; 10 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenPreviewRespVO;
9 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO; 11 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO;
10 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO; 12 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO;
11 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTableRespVO; 13 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTableRespVO;
12 -import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.SchemaTableRespVO; 14 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.DatabaseTableRespVO;
13 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert; 15 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert;
14 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO; 16 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO;
15 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO; 17 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
16 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
17 import cn.iocoder.yudao.module.infra.service.codegen.CodegenService; 18 import cn.iocoder.yudao.module.infra.service.codegen.CodegenService;
18 -import cn.iocoder.yudao.framework.common.util.collection.CollectionUtils;  
19 -import cn.iocoder.yudao.framework.common.util.servlet.ServletUtils;  
20 import io.swagger.annotations.Api; 19 import io.swagger.annotations.Api;
21 import io.swagger.annotations.ApiImplicitParam; 20 import io.swagger.annotations.ApiImplicitParam;
22 import io.swagger.annotations.ApiImplicitParams; 21 import io.swagger.annotations.ApiImplicitParams;
@@ -33,7 +32,6 @@ import java.io.ByteArrayOutputStream; @@ -33,7 +32,6 @@ import java.io.ByteArrayOutputStream;
33 import java.io.IOException; 32 import java.io.IOException;
34 import java.util.List; 33 import java.util.List;
35 import java.util.Map; 34 import java.util.Map;
36 -import java.util.Set;  
37 35
38 import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; 36 import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
39 import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId; 37 import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
@@ -51,20 +49,15 @@ public class CodegenController { @@ -51,20 +49,15 @@ public class CodegenController {
51 @ApiOperation(value = "获得数据库自带的表定义列表", notes = "会过滤掉已经导入 Codegen 的表") 49 @ApiOperation(value = "获得数据库自带的表定义列表", notes = "会过滤掉已经导入 Codegen 的表")
52 @ApiImplicitParams({ 50 @ApiImplicitParams({
53 @ApiImplicitParam(name = "dataSourceConfigId", value = "数据源配置的编号", required = true, example = "1", dataTypeClass = Long.class), 51 @ApiImplicitParam(name = "dataSourceConfigId", value = "数据源配置的编号", required = true, example = "1", dataTypeClass = Long.class),
54 - @ApiImplicitParam(name = "tableName", value = "表名,模糊匹配", example = "yudao", dataTypeClass = String.class),  
55 - @ApiImplicitParam(name = "tableComment", value = "描述,模糊匹配", example = "芋道", dataTypeClass = String.class) 52 + @ApiImplicitParam(name = "name", value = "表名,模糊匹配", example = "yudao", dataTypeClass = String.class),
  53 + @ApiImplicitParam(name = "comment", value = "描述,模糊匹配", example = "芋道", dataTypeClass = String.class)
56 }) 54 })
57 @PreAuthorize("@ss.hasPermission('infra:codegen:query')") 55 @PreAuthorize("@ss.hasPermission('infra:codegen:query')")
58 - public CommonResult<List<SchemaTableRespVO>> getSchemaTableList( 56 + public CommonResult<List<DatabaseTableRespVO>> getDatabaseTableList(
59 @RequestParam(value = "dataSourceConfigId") Long dataSourceConfigId, 57 @RequestParam(value = "dataSourceConfigId") Long dataSourceConfigId,
60 - @RequestParam(value = "tableName", required = false) String tableName,  
61 - @RequestParam(value = "tableComment", required = false) String tableComment) {  
62 - // 获得数据库自带的表定义列表  
63 - List<DatabaseTableDO> schemaTables = codegenService.getSchemaTableList(dataSourceConfigId, tableName, tableComment);  
64 - // 移除在 Codegen 中,已经存在的  
65 - Set<String> existsTables = CollectionUtils.convertSet(codegenService.getCodeGenTableList(), CodegenTableDO::getTableName);  
66 - schemaTables.removeIf(table -> existsTables.contains(table.getTableName()));  
67 - return success(CodegenConvert.INSTANCE.convertList04(schemaTables)); 58 + @RequestParam(value = "name", required = false) String name,
  59 + @RequestParam(value = "comment", required = false) String comment) {
  60 + return success(codegenService.getDatabaseTableList(dataSourceConfigId, name, comment));
68 } 61 }
69 62
70 @GetMapping("/table/page") 63 @GetMapping("/table/page")
@@ -87,19 +80,10 @@ public class CodegenController { @@ -87,19 +80,10 @@ public class CodegenController {
87 } 80 }
88 81
89 @ApiOperation("基于数据库的表结构,创建代码生成器的表和字段定义") 82 @ApiOperation("基于数据库的表结构,创建代码生成器的表和字段定义")
90 - @ApiImplicitParam(name = "tableNames", value = "表名数组", required = true, example = "sys_user", dataTypeClass = List.class)  
91 - @PostMapping("/create-list-from-db")  
92 - @PreAuthorize("@ss.hasPermission('infra:codegen:create')")  
93 - public CommonResult<List<Long>> createCodegenListFromDB(@RequestParam("tableNames") List<String> tableNames) {  
94 - return success(codegenService.createCodegenListFromDB(getLoginUserId(), tableNames));  
95 - }  
96 -  
97 - @ApiOperation("基于 SQL 建表语句,创建代码生成器的表和字段定义")  
98 - @ApiImplicitParam(name = "sql", value = "SQL 建表语句", required = true, example = "sql", dataTypeClass = String.class)  
99 - @PostMapping("/create-list-from-sql") 83 + @PostMapping("/create-list")
100 @PreAuthorize("@ss.hasPermission('infra:codegen:create')") 84 @PreAuthorize("@ss.hasPermission('infra:codegen:create')")
101 - public CommonResult<Long> createCodegenListFromSQL(@RequestParam("sql") String sql) {  
102 - return success(codegenService.createCodegenListFromSQL(getLoginUserId(), sql)); 85 + public CommonResult<List<Long>> createCodegenList(@Valid @RequestBody CodegenCreateListReqVO reqVO) {
  86 + return success(codegenService.createCodegenList(getLoginUserId(), reqVO));
103 } 87 }
104 88
105 @ApiOperation("更新数据库的表和字段定义") 89 @ApiOperation("更新数据库的表和字段定义")
@@ -119,19 +103,6 @@ public class CodegenController { @@ -119,19 +103,6 @@ public class CodegenController {
119 return success(true); 103 return success(true);
120 } 104 }
121 105
122 - @ApiOperation("基于 SQL 建表语句,同步数据库的表和字段定义")  
123 - @PutMapping("/sync-from-sql")  
124 - @ApiImplicitParams({  
125 - @ApiImplicitParam(name = "tableId", value = "表编号", required = true, example = "1024", dataTypeClass = Long.class),  
126 - @ApiImplicitParam(name = "sql", value = "SQL 建表语句", required = true, example = "sql", dataTypeClass = String.class)  
127 - })  
128 - @PreAuthorize("@ss.hasPermission('infra:codegen:update')")  
129 - public CommonResult<Boolean> syncCodegenFromSQL(@RequestParam("tableId") Long tableId,  
130 - @RequestParam("sql") String sql) {  
131 - codegenService.syncCodegenFromSQL(tableId, sql);  
132 - return success(true);  
133 - }  
134 -  
135 @ApiOperation("删除数据库的表和字段定义") 106 @ApiOperation("删除数据库的表和字段定义")
136 @DeleteMapping("/delete") 107 @DeleteMapping("/delete")
137 @ApiImplicitParam(name = "tableId", value = "表编号", required = true, example = "1024", dataTypeClass = Long.class) 108 @ApiImplicitParam(name = "tableId", value = "表编号", required = true, example = "1024", dataTypeClass = Long.class)
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/vo/CodegenCreateListReqVO.java 0 → 100644
  1 +package cn.iocoder.yudao.module.infra.controller.admin.codegen.vo;
  2 +
  3 +import io.swagger.annotations.ApiModel;
  4 +import io.swagger.annotations.ApiModelProperty;
  5 +import lombok.Data;
  6 +
  7 +import javax.validation.constraints.NotNull;
  8 +import java.util.List;
  9 +
  10 +@ApiModel("管理后台 - 基于数据库的表结构,创建代码生成器的表和字段定义 Request VO")
  11 +@Data
  12 +public class CodegenCreateListReqVO {
  13 +
  14 + @ApiModelProperty(value = "数据源配置的编号", required = true, example = "1")
  15 + @NotNull(message = "数据源配置的编号不能为空")
  16 + private Long dataSourceConfigId;
  17 +
  18 + @ApiModelProperty(value = "表名数组", required = true, example = "[1, 2, 3]")
  19 + @NotNull(message = "表名数组不能为空")
  20 + private List<String> tableNames;
  21 +
  22 +}
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/vo/table/CodegenTableBaseVO.java
@@ -12,10 +12,6 @@ import javax.validation.constraints.NotNull; @@ -12,10 +12,6 @@ import javax.validation.constraints.NotNull;
12 @Data 12 @Data
13 public class CodegenTableBaseVO { 13 public class CodegenTableBaseVO {
14 14
15 - @ApiModelProperty(value = "导入类型", required = true, example = "1", notes = "参见 CodegenImportTypeEnum 枚举")  
16 - @NotNull(message = "导入类型不能为空")  
17 - private Integer importType;  
18 -  
19 @ApiModelProperty(value = "生成场景", required = true, example = "1", notes = "参见 CodegenSceneEnum 枚举") 15 @ApiModelProperty(value = "生成场景", required = true, example = "1", notes = "参见 CodegenSceneEnum 枚举")
20 @NotNull(message = "导入类型不能为空") 16 @NotNull(message = "导入类型不能为空")
21 private Integer scene; 17 private Integer scene;
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/vo/table/CodegenTableRespVO.java
@@ -17,6 +17,9 @@ public class CodegenTableRespVO extends CodegenTableBaseVO { @@ -17,6 +17,9 @@ public class CodegenTableRespVO extends CodegenTableBaseVO {
17 @ApiModelProperty(value = "编号", required = true, example = "1") 17 @ApiModelProperty(value = "编号", required = true, example = "1")
18 private Long id; 18 private Long id;
19 19
  20 + @ApiModelProperty(value = "主键编号", required = true, example = "1024")
  21 + private Integer dataSourceConfigId;
  22 +
20 @ApiModelProperty(value = "创建时间", required = true) 23 @ApiModelProperty(value = "创建时间", required = true)
21 private Date createTime; 24 private Date createTime;
22 25
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/vo/table/SchemaTableRespVO.java renamed to yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/controller/admin/codegen/vo/table/DatabaseTableRespVO.java
@@ -4,22 +4,14 @@ import io.swagger.annotations.ApiModel; @@ -4,22 +4,14 @@ import io.swagger.annotations.ApiModel;
4 import io.swagger.annotations.ApiModelProperty; 4 import io.swagger.annotations.ApiModelProperty;
5 import lombok.Data; 5 import lombok.Data;
6 6
7 -import java.util.Date;  
8 -  
9 -@ApiModel("管理后台 - 数据字典的表定义 Response VO") 7 +@ApiModel("管理后台 - 数据库的表定义 Response VO")
10 @Data 8 @Data
11 -public class SchemaTableRespVO {  
12 -  
13 - @ApiModelProperty(value = "数据库", required = true, example = "yudao")  
14 - private String tableSchema; 9 +public class DatabaseTableRespVO {
15 10
16 @ApiModelProperty(value = "表名称", required = true, example = "yuanma") 11 @ApiModelProperty(value = "表名称", required = true, example = "yuanma")
17 - private String tableName; 12 + private String name;
18 13
19 @ApiModelProperty(value = "表描述", required = true, example = "芋道源码") 14 @ApiModelProperty(value = "表描述", required = true, example = "芋道源码")
20 - private String tableComment;  
21 -  
22 - @ApiModelProperty(value = "创建时间", required = true)  
23 - private Date createTime; 15 + private String comment;
24 16
25 } 17 }
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/convert/codegen/CodegenConvert.java
@@ -6,12 +6,14 @@ import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenPreviewR @@ -6,12 +6,14 @@ import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenPreviewR
6 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO; 6 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO;
7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.column.CodegenColumnRespVO; 7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.column.CodegenColumnRespVO;
8 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTableRespVO; 8 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTableRespVO;
9 -import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.SchemaTableRespVO; 9 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.DatabaseTableRespVO;
10 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO; 10 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO;
11 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO; 11 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
12 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
13 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO; 12 +import com.baomidou.mybatisplus.generator.config.po.TableField;
  13 +import com.baomidou.mybatisplus.generator.config.po.TableInfo;
14 import org.mapstruct.Mapper; 14 import org.mapstruct.Mapper;
  15 +import org.mapstruct.Mapping;
  16 +import org.mapstruct.Mappings;
15 import org.mapstruct.factory.Mappers; 17 import org.mapstruct.factory.Mappers;
16 18
17 import java.util.List; 19 import java.util.List;
@@ -23,13 +25,27 @@ public interface CodegenConvert { @@ -23,13 +25,27 @@ public interface CodegenConvert {
23 25
24 CodegenConvert INSTANCE = Mappers.getMapper(CodegenConvert.class); 26 CodegenConvert INSTANCE = Mappers.getMapper(CodegenConvert.class);
25 27
26 - // ========== InformationSchemaTableDO 和 InformationSchemaColumnDO 相关 ========== 28 + // ========== TableInfo 相关 ==========
27 29
28 - CodegenTableDO convert(DatabaseTableDO bean); 30 + @Mappings({
  31 + @Mapping(source = "name", target = "tableName"),
  32 + @Mapping(source = "comment", target = "tableComment"),
  33 + })
  34 + CodegenTableDO convert(TableInfo bean);
29 35
30 - List<CodegenColumnDO> convertList(List<DatabaseColumnDO> list); 36 + List<CodegenColumnDO> convertList(List<TableField> list);
31 37
32 - CodegenTableRespVO convert(DatabaseColumnDO bean); 38 + @Mappings({
  39 + @Mapping(source = "name", target = "columnName"),
  40 + @Mapping(source = "type", target = "dataType"),
  41 + @Mapping(source = "comment", target = "columnComment"),
  42 + @Mapping(source = "metaInfo.nullable", target = "nullable"),
  43 + @Mapping(source = "keyFlag", target = "primaryKey"),
  44 + @Mapping(source = "keyIdentityFlag", target = "autoIncrement"),
  45 + @Mapping(source = "columnType.type", target = "javaType"),
  46 + @Mapping(source = "propertyName", target = "javaField"),
  47 + })
  48 + CodegenColumnDO convert(TableField bean);
33 49
34 // ========== CodegenTableDO 相关 ========== 50 // ========== CodegenTableDO 相关 ==========
35 51
@@ -47,7 +63,7 @@ public interface CodegenConvert { @@ -47,7 +63,7 @@ public interface CodegenConvert {
47 63
48 List<CodegenColumnDO> convertList03(List<CodegenUpdateReqVO.Column> columns); 64 List<CodegenColumnDO> convertList03(List<CodegenUpdateReqVO.Column> columns);
49 65
50 - List<SchemaTableRespVO> convertList04(List<DatabaseTableDO> list); 66 + List<DatabaseTableRespVO> convertList04(List<TableInfo> list);
51 67
52 // ========== 其它 ========== 68 // ========== 其它 ==========
53 69
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenTableDO.java
1 package cn.iocoder.yudao.module.infra.dal.dataobject.codegen; 1 package cn.iocoder.yudao.module.infra.dal.dataobject.codegen;
2 2
3 import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO; 3 import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
  4 +import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO;
4 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenSceneEnum; 5 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenSceneEnum;
5 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenTemplateTypeEnum; 6 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenTemplateTypeEnum;
6 import com.baomidou.mybatisplus.annotation.TableName; 7 import com.baomidou.mybatisplus.annotation.TableName;
@@ -25,11 +26,11 @@ public class CodegenTableDO extends BaseDO { @@ -25,11 +26,11 @@ public class CodegenTableDO extends BaseDO {
25 private Long id; 26 private Long id;
26 27
27 /** 28 /**
28 - * 导入类型 29 + * 数据源编号
29 * 30 *
30 - * 枚举 {@link CodegenTemplateTypeEnum} 31 + * 关联 {@link DataSourceConfigDO#getId()}
31 */ 32 */
32 - private Integer importType; 33 + private Long dataSourceConfigId;
33 /** 34 /**
34 * 生成场景 35 * 生成场景
35 * 36 *
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/db/DatabaseColumnDO.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.dataobject.db;  
2 -  
3 -import com.baomidou.mybatisplus.annotation.TableField;  
4 -import com.baomidou.mybatisplus.annotation.TableName;  
5 -import lombok.Builder;  
6 -import lombok.Data;  
7 -  
8 -/**  
9 - * MySQL 数据库中的 column 字段定义  
10 - *  
11 - * @author 芋道源码  
12 - */  
13 -@Data  
14 -@Builder  
15 -public class DatabaseColumnDO {  
16 -  
17 - /**  
18 - * 表名称  
19 - */  
20 - private String tableName;  
21 - /**  
22 - * 字段名  
23 - */  
24 - private String columnName;  
25 - /**  
26 - * 字段类型  
27 - */  
28 - private String dataType;  
29 - /**  
30 - * 字段描述  
31 - */  
32 - private String columnComment;  
33 - /**  
34 - * 是否允许为空  
35 - */  
36 - private Boolean nullable;  
37 - /**  
38 - * 是否主键  
39 - */  
40 - private Boolean primaryKey;  
41 - /**  
42 - * 是否自增  
43 - */  
44 - private Boolean autoIncrement;  
45 - /**  
46 - * 排序字段  
47 - */  
48 - private Integer ordinalPosition;  
49 -  
50 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/db/DatabaseTableDO.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.dataobject.db;  
2 -  
3 -import lombok.Builder;  
4 -import lombok.Data;  
5 -  
6 -import java.util.Date;  
7 -  
8 -/**  
9 - * MySQL 数据库中的 table 表定义  
10 - *  
11 - * @author 芋道源码  
12 - */  
13 -@Data  
14 -@Builder  
15 -public class DatabaseTableDO {  
16 -  
17 - /**  
18 - * 表名称  
19 - */  
20 - private String tableName;  
21 - /**  
22 - * 表描述  
23 - */  
24 - private String tableComment;  
25 - /**  
26 - * 创建时间  
27 - */  
28 - private Date createTime;  
29 -  
30 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/mysql/codegen/CodegenTableMapper.java
@@ -3,16 +3,18 @@ package cn.iocoder.yudao.module.infra.dal.mysql.codegen; @@ -3,16 +3,18 @@ package cn.iocoder.yudao.module.infra.dal.mysql.codegen;
3 import cn.iocoder.yudao.framework.common.pojo.PageResult; 3 import cn.iocoder.yudao.framework.common.pojo.PageResult;
4 import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX; 4 import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
5 import cn.iocoder.yudao.framework.mybatis.core.query.QueryWrapperX; 5 import cn.iocoder.yudao.framework.mybatis.core.query.QueryWrapperX;
6 -import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;  
7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO; 6 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO;
8 -import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; 7 +import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
9 import org.apache.ibatis.annotations.Mapper; 8 import org.apache.ibatis.annotations.Mapper;
10 9
  10 +import java.util.List;
  11 +
11 @Mapper 12 @Mapper
12 public interface CodegenTableMapper extends BaseMapperX<CodegenTableDO> { 13 public interface CodegenTableMapper extends BaseMapperX<CodegenTableDO> {
13 14
14 - default CodegenTableDO selectByTableName(String tableName) {  
15 - return selectOne(new QueryWrapper<CodegenTableDO>().eq("table_name", tableName)); 15 + default CodegenTableDO selectByTableNameAndDataSourceConfigId(String tableName, Long dataSourceConfigId) {
  16 + return selectOne(CodegenTableDO::getTableName, tableName,
  17 + CodegenTableDO::getDataSourceConfigId, dataSourceConfigId);
16 } 18 }
17 19
18 default PageResult<CodegenTableDO> selectPage(CodegenTablePageReqVO pageReqVO) { 20 default PageResult<CodegenTableDO> selectPage(CodegenTablePageReqVO pageReqVO) {
@@ -22,4 +24,8 @@ public interface CodegenTableMapper extends BaseMapperX&lt;CodegenTableDO&gt; { @@ -22,4 +24,8 @@ public interface CodegenTableMapper extends BaseMapperX&lt;CodegenTableDO&gt; {
22 .betweenIfPresent("create_time", pageReqVO.getBeginCreateTime(), pageReqVO.getEndCreateTime())); 24 .betweenIfPresent("create_time", pageReqVO.getBeginCreateTime(), pageReqVO.getEndCreateTime()));
23 } 25 }
24 26
  27 + default List<CodegenTableDO> selectListByDataSourceConfigId(Long dataSourceConfigId) {
  28 + return selectList(CodegenTableDO::getDataSourceConfigId, dataSourceConfigId);
  29 + }
  30 +
25 } 31 }
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/mysql/db/DatabaseTableDAO.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.mysql.db;  
2 -  
3 -import cn.hutool.core.collection.CollUtil;  
4 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
5 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
6 -import com.baomidou.mybatisplus.annotation.DbType;  
7 -  
8 -import java.sql.Connection;  
9 -import java.util.List;  
10 -  
11 -/**  
12 - * 数据库 Table DAO 接口  
13 - *  
14 - * @author 芋道源码  
15 - */  
16 -public interface DatabaseTableDAO {  
17 -  
18 - /**  
19 - * 获得表列表,基于表名称 + 表描述进行模糊匹配  
20 - *  
21 - * @param connection 数据库连接  
22 - * @param tableNameLike 表名称,模糊匹配  
23 - * @param tableCommentLike 表描述,模糊匹配  
24 - * @return 表列表  
25 - */  
26 - List<DatabaseTableDO> selectTableList(Connection connection, String tableNameLike, String tableCommentLike);  
27 -  
28 - /**  
29 - * 获得指定表名  
30 - *  
31 - * @param connection 数据库连接  
32 - * @param tableName 表名称  
33 - * @return 表  
34 - */  
35 - default DatabaseTableDO selectTable(Connection connection, String tableName) {  
36 - // 考虑到对性能没有要求,直接查询列表,然后内存过滤到记录  
37 - List<DatabaseTableDO> tables = selectTableList(connection, tableName, null);  
38 - return CollUtil.findOne(tables, table -> table.getTableName().equalsIgnoreCase(tableName));  
39 - }  
40 -  
41 - /**  
42 - * 获得指定表的字段列表  
43 - *  
44 - * @param connection 数据库连接  
45 - * @param tableName 表名称  
46 - * @return 字段列表  
47 - */  
48 - List<DatabaseColumnDO> selectColumnList(Connection connection, String tableName);  
49 -  
50 - /**  
51 - * 获得数据库的类型  
52 - *  
53 - * @return 数据库的类型  
54 - */  
55 - DbType getType();  
56 -  
57 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/mysql/db/DatabaseTableMySQLDAOImpl.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.mysql.db;  
2 -  
3 -import cn.hutool.core.util.StrUtil;  
4 -import cn.iocoder.yudao.framework.mybatis.core.util.JdbcUtils;  
5 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
6 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
7 -import com.baomidou.mybatisplus.annotation.DbType;  
8 -import org.springframework.stereotype.Repository;  
9 -  
10 -import java.sql.Connection;  
11 -import java.util.List;  
12 -  
13 -/**  
14 - * {@link DatabaseTableDAO} 的 MySQL 实现类  
15 - *  
16 - * @author 芋道源码  
17 - */  
18 -@Repository  
19 -public class DatabaseTableMySQLDAOImpl implements DatabaseTableDAO {  
20 -  
21 - @Override  
22 - public List<DatabaseTableDO> selectTableList(Connection connection, String tableNameLike, String tableCommentLike) {  
23 - // 拼接 SQL  
24 - String sql = "SELECT table_name, table_comment, create_time" +  
25 - " FROM information_schema.TABLES" +  
26 - " WHERE table_schema = (SELECT DATABASE())";  
27 - if (StrUtil.isNotEmpty(tableNameLike)) {  
28 - sql += StrUtil.format(" AND table_name LIKE '%{}%'", tableNameLike);  
29 - }  
30 - if (StrUtil.isNotEmpty(tableCommentLike)) {  
31 - sql += StrUtil.format(" AND table_comment LIKE '%{}%'", tableCommentLike);  
32 - }  
33 - // 执行并返回结果  
34 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseTableDO.builder()  
35 - .tableName(rs.getString("table_name"))  
36 - .tableComment(rs.getString("table_comment"))  
37 - .createTime(rs.getDate("create_time"))  
38 - .build());  
39 - }  
40 -  
41 - @Override  
42 - public List<DatabaseColumnDO> selectColumnList(Connection connection, String tableName) {  
43 - // 拼接 SQL  
44 - String sql = "SELECT table_name, column_name, data_type, column_comment, ordinal_position," +  
45 - " (CASE WHEN is_nullable = 'yes' THEN '1' ELSE '0' END) AS nullable," +  
46 - " (CASE WHEN column_key = 'PRI' THEN '1' ELSE '0' END) AS primary_key," +  
47 - " (CASE WHEN extra = 'auto_increment' THEN '1' ELSE '0' END) AS auto_increment" +  
48 - " FROM information_schema.COLUMNS" +  
49 - " WHERE table_schema = (SELECT DATABASE())" +  
50 - String.format(" AND table_name = '%s'", tableName);  
51 - // 执行并返回结果  
52 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseColumnDO.builder()  
53 - .tableName(rs.getString("table_name"))  
54 - .columnName(rs.getString("column_name"))  
55 - .dataType(rs.getString("data_type"))  
56 - .columnComment(rs.getString("column_comment"))  
57 - .nullable(rs.getBoolean("nullable"))  
58 - .primaryKey(rs.getBoolean("primary_key"))  
59 - .autoIncrement(rs.getBoolean("auto_increment"))  
60 - .ordinalPosition(rs.getInt("ordinal_position"))  
61 - .build());  
62 - }  
63 -  
64 - @Override  
65 - public DbType getType() {  
66 - return DbType.MYSQL;  
67 - }  
68 -  
69 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/mysql/db/DatabaseTableOracleDAOImpl.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.mysql.db;  
2 -  
3 -import cn.hutool.core.util.StrUtil;  
4 -import cn.iocoder.yudao.framework.mybatis.core.util.JdbcUtils;  
5 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
6 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
7 -import com.baomidou.mybatisplus.annotation.DbType;  
8 -import org.springframework.stereotype.Repository;  
9 -  
10 -import java.sql.Connection;  
11 -import java.util.List;  
12 -  
13 -/**  
14 - * {@link DatabaseTableDAO} 的 Oracle 实现类  
15 - *  
16 - * @author 芋道源码  
17 - */  
18 -@Repository  
19 -public class DatabaseTableOracleDAOImpl implements DatabaseTableDAO {  
20 -  
21 - @Override  
22 - public List<DatabaseTableDO> selectTableList(Connection connection, String tableNameLike, String tableCommentLike) {  
23 - // 拼接 SQL  
24 - String sql = "SELECT tbl.table_name, col.comments, obj.created" +  
25 - " FROM user_tables tbl, user_tab_comments col, user_objects obj" +  
26 - " WHERE tbl.table_name = col.table_name" +  
27 - " AND tbl.table_name = obj.object_name" +  
28 - " AND obj.object_type = 'TABLE'";  
29 - if (StrUtil.isNotEmpty(tableNameLike)) {  
30 - sql += StrUtil.format(" AND tbl.table_name LIKE '%{}%'", tableNameLike);  
31 - }  
32 - if (StrUtil.isNotEmpty(tableCommentLike)) {  
33 - sql += StrUtil.format(" AND col.comments LIKE '%{}%'", tableCommentLike);  
34 - }  
35 - // 执行并返回结果  
36 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseTableDO.builder()  
37 - .tableName(rs.getString("table_name"))  
38 - .tableComment(rs.getString("comments"))  
39 - .createTime(rs.getDate("created"))  
40 - .build());  
41 - }  
42 -  
43 - @Override  
44 - public List<DatabaseColumnDO> selectColumnList(Connection connection, String tableName) {  
45 - // 拼接 SQL  
46 - String sql = String.format("SELECT table_name, column_name, data_type, comments, column_id," +  
47 - " (CASE WHEN nullable = 'Y' THEN '1' ELSE '0' END) AS nullable," +  
48 - " (CASE WHEN constraint_type = 'P' THEN '1' ELSE '0' END) AS primary_key" +  
49 - " FROM" +  
50 - " (" +  
51 - " SELECT col.*, comments, constraint_type," +  
52 - " row_number ( ) over ( partition BY col.column_name ORDER BY constraint_type DESC ) AS row_flag" +  
53 - " FROM user_tab_columns col" +  
54 - " LEFT JOIN user_col_comments ON user_col_comments.table_name = col.table_name" +  
55 - " AND user_col_comments.column_name = col.column_name" +  
56 - " LEFT JOIN user_cons_columns ON user_cons_columns.table_name = col.table_name" +  
57 - " AND user_cons_columns.column_name = col.column_name" +  
58 - " LEFT JOIN user_constraints ON user_constraints.constraint_name = user_cons_columns.constraint_name" +  
59 - " WHERE col.table_name = '%s'" +  
60 - " )" +  
61 - "WHERE row_flag = 1", tableName);  
62 - // 执行并返回结果  
63 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseColumnDO.builder()  
64 - .tableName(rs.getString("table_name"))  
65 - .columnName(rs.getString("column_name"))  
66 - .dataType(rs.getString("data_type"))  
67 - .columnComment(rs.getString("comments"))  
68 - .nullable(rs.getBoolean("nullable"))  
69 - .primaryKey(rs.getBoolean("primary_key"))  
70 - .autoIncrement(false) // TODO 芋艿:oracle???  
71 - .ordinalPosition(rs.getInt("column_id"))  
72 - .build());  
73 - }  
74 -  
75 - @Override  
76 - public DbType getType() {  
77 - return DbType.ORACLE;  
78 - }  
79 -  
80 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/mysql/db/DatabaseTablePostgreSQLDAOImpl.java deleted
1 -package cn.iocoder.yudao.module.infra.dal.mysql.db;  
2 -  
3 -import cn.hutool.core.util.StrUtil;  
4 -import cn.iocoder.yudao.framework.mybatis.core.util.JdbcUtils;  
5 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
6 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
7 -import com.baomidou.mybatisplus.annotation.DbType;  
8 -import org.springframework.stereotype.Repository;  
9 -  
10 -import java.sql.Connection;  
11 -import java.util.List;  
12 -  
13 -/**  
14 - * {@link DatabaseTableDAO} 的 PostgreSQL 实现类  
15 - *  
16 - * @author 芋道源码  
17 - */  
18 -@Repository  
19 -public class DatabaseTablePostgreSQLDAOImpl implements DatabaseTableDAO {  
20 -  
21 - @Override  
22 - public List<DatabaseTableDO> selectTableList(Connection connection, String tableNameLike, String tableCommentLike) {  
23 - // 拼接 SQL  
24 - String sql = "SELECT tbl.tablename, obj_description(c.oid)" +  
25 - " FROM pg_tables tbl, pg_class c" +  
26 - " WHERE tbl.schemaname = CURRENT_SCHEMA()" +  
27 - " AND tbl.tablename = c.relname";  
28 - if (StrUtil.isNotEmpty(tableNameLike)) {  
29 - sql += StrUtil.format(" AND tbl.tablename LIKE '%{}%'", tableNameLike);  
30 - }  
31 - if (StrUtil.isNotEmpty(tableCommentLike)) {  
32 - sql += StrUtil.format(" AND obj_description(c.oid) LIKE '%{}%'", tableCommentLike);  
33 - }  
34 - // 执行并返回结果  
35 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseTableDO.builder()  
36 - .tableName(rs.getString("tablename"))  
37 - .tableComment(rs.getString("obj_description"))  
38 - .build());  
39 - }  
40 -  
41 - @Override  
42 - public List<DatabaseColumnDO> selectColumnList(Connection connection, String tableName) {  
43 - // 拼接 SQL  
44 - String sql = "SELECT table_name, column_name, data_type, column_comment, ordinal_position," +  
45 - " (CASE WHEN is_nullable = 'yes' THEN '1' ELSE '0' END) AS nullable," +  
46 - " (CASE WHEN column_key = 'PRI' THEN '1' ELSE '0' END) AS primary_key," +  
47 - " (CASE WHEN extra = 'auto_increment' THEN '1' ELSE '0' END) AS auto_increment" +  
48 - " FROM information_schema.COLUMNS" +  
49 - " WHERE table_schema = (SELECT DATABASE())" +  
50 - String.format(" AND table_name = '%s'", tableName);  
51 - // 执行并返回结果  
52 - return JdbcUtils.query(connection, sql, (rs, rowNum) -> DatabaseColumnDO.builder()  
53 - .tableName(rs.getString("table_name"))  
54 - .columnName(rs.getString("column_name"))  
55 - .dataType(rs.getString("data_type"))  
56 - .columnComment(rs.getString("column_comment"))  
57 - .nullable(rs.getBoolean("nullable"))  
58 - .primaryKey(rs.getBoolean("primary_key"))  
59 - .autoIncrement(rs.getBoolean("auto_increment"))  
60 - .ordinalPosition(rs.getInt("ordinal_position"))  
61 - .build());  
62 - }  
63 -  
64 - @Override  
65 - public DbType getType() {  
66 - return DbType.MYSQL;  
67 - }  
68 -  
69 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/enums/codegen/CodegenImportTypeEnum.java deleted
1 -package cn.iocoder.yudao.module.infra.enums.codegen;  
2 -  
3 -import lombok.AllArgsConstructor;  
4 -import lombok.Getter;  
5 -  
6 -/**  
7 - * 代码生成的导入类型  
8 - *  
9 - * @author 芋道源码  
10 - */  
11 -@AllArgsConstructor  
12 -@Getter  
13 -public enum CodegenImportTypeEnum {  
14 -  
15 - DB(1), // 从 information_schema 的 table 和 columns 表导入  
16 - SQL(2); // 基于建表 SQL 语句导入  
17 -  
18 - /**  
19 - * 类型  
20 - */  
21 - private final Integer type;  
22 -  
23 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenService.java
1 package cn.iocoder.yudao.module.infra.service.codegen; 1 package cn.iocoder.yudao.module.infra.service.codegen;
2 2
3 import cn.iocoder.yudao.framework.common.pojo.PageResult; 3 import cn.iocoder.yudao.framework.common.pojo.PageResult;
  4 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenCreateListReqVO;
4 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO; 5 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO;
5 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO; 6 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO;
  7 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.DatabaseTableRespVO;
6 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO; 8 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO;
7 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO; 9 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
8 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
9 10
10 import java.util.List; 11 import java.util.List;
11 import java.util.Map; 12 import java.util.Map;
@@ -18,31 +19,13 @@ import java.util.Map; @@ -18,31 +19,13 @@ import java.util.Map;
18 public interface CodegenService { 19 public interface CodegenService {
19 20
20 /** 21 /**
21 - * 基于 SQL 建表语句,创建代码生成器的表定义  
22 - *  
23 - * @param userId 用户编号  
24 - * @param sql SQL 建表语句  
25 - * @return 创建的表定义的编号  
26 - */  
27 - Long createCodegenListFromSQL(Long userId, String sql);  
28 -  
29 - /**  
30 * 基于数据库的表结构,创建代码生成器的表定义 22 * 基于数据库的表结构,创建代码生成器的表定义
31 * 23 *
32 * @param userId 用户编号 24 * @param userId 用户编号
33 - * @param tableName 表名称  
34 - * @return 创建的表定义的编号  
35 - */  
36 - Long createCodegen(Long userId, String tableName);  
37 -  
38 - /**  
39 - * 基于 {@link #createCodegen(Long, String)} 的批量创建  
40 - *  
41 - * @param userId 用户编号  
42 - * @param tableNames 表名称数组 25 + * @param reqVO 表信息
43 * @return 创建的表定义的编号数组 26 * @return 创建的表定义的编号数组
44 */ 27 */
45 - List<Long> createCodegenListFromDB(Long userId, List<String> tableNames); 28 + List<Long> createCodegenList(Long userId, CodegenCreateListReqVO reqVO);
46 29
47 /** 30 /**
48 * 更新数据库的表和字段定义 31 * 更新数据库的表和字段定义
@@ -59,14 +42,6 @@ public interface CodegenService { @@ -59,14 +42,6 @@ public interface CodegenService {
59 void syncCodegenFromDB(Long tableId); 42 void syncCodegenFromDB(Long tableId);
60 43
61 /** 44 /**
62 - * 基于 SQL 建表语句,同步数据库的表和字段定义  
63 - *  
64 - * @param tableId 表编号  
65 - * @param sql SQL 建表语句  
66 - */  
67 - void syncCodegenFromSQL(Long tableId, String sql);  
68 -  
69 - /**  
70 * 删除数据库的表和字段定义 45 * 删除数据库的表和字段定义
71 * 46 *
72 * @param tableId 数据编号 47 * @param tableId 数据编号
@@ -90,13 +65,6 @@ public interface CodegenService { @@ -90,13 +65,6 @@ public interface CodegenService {
90 CodegenTableDO getCodegenTablePage(Long id); 65 CodegenTableDO getCodegenTablePage(Long id);
91 66
92 /** 67 /**
93 - * 获得全部表定义  
94 - *  
95 - * @return 表定义数组  
96 - */  
97 - List<CodegenTableDO> getCodeGenTableList();  
98 -  
99 - /**  
100 * 获得指定表的字段定义数组 68 * 获得指定表的字段定义数组
101 * 69 *
102 * @param tableId 表编号 70 * @param tableId 表编号
@@ -116,11 +84,11 @@ public interface CodegenService { @@ -116,11 +84,11 @@ public interface CodegenService {
116 * 获得数据库自带的表定义列表 84 * 获得数据库自带的表定义列表
117 * 85 *
118 * 86 *
119 - * @param dataSourceConfigId  
120 - * @param tableName 表名称  
121 - * @param tableComment 表描述 87 + * @param dataSourceConfigId 数据源的配置编号
  88 + * @param name 表名称
  89 + * @param comment 表描述
122 * @return 表定义列表 90 * @return 表定义列表
123 */ 91 */
124 - List<DatabaseTableDO> getSchemaTableList(Long dataSourceConfigId, String tableName, String tableComment); 92 + List<DatabaseTableRespVO> getDatabaseTableList(Long dataSourceConfigId, String name, String comment);
125 93
126 } 94 }
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenServiceImpl.java
@@ -3,22 +3,21 @@ package cn.iocoder.yudao.module.infra.service.codegen; @@ -3,22 +3,21 @@ package cn.iocoder.yudao.module.infra.service.codegen;
3 import cn.hutool.core.collection.CollUtil; 3 import cn.hutool.core.collection.CollUtil;
4 import cn.iocoder.yudao.framework.common.pojo.PageResult; 4 import cn.iocoder.yudao.framework.common.pojo.PageResult;
5 import cn.iocoder.yudao.framework.common.util.collection.CollectionUtils; 5 import cn.iocoder.yudao.framework.common.util.collection.CollectionUtils;
  6 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenCreateListReqVO;
6 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO; 7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.CodegenUpdateReqVO;
7 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO; 8 import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.CodegenTablePageReqVO;
  9 +import cn.iocoder.yudao.module.infra.controller.admin.codegen.vo.table.DatabaseTableRespVO;
8 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert; 10 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert;
9 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO; 11 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO;
10 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO; 12 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
11 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
12 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
13 import cn.iocoder.yudao.module.infra.dal.mysql.codegen.CodegenColumnMapper; 13 import cn.iocoder.yudao.module.infra.dal.mysql.codegen.CodegenColumnMapper;
14 import cn.iocoder.yudao.module.infra.dal.mysql.codegen.CodegenTableMapper; 14 import cn.iocoder.yudao.module.infra.dal.mysql.codegen.CodegenTableMapper;
15 -import cn.iocoder.yudao.module.infra.enums.codegen.CodegenImportTypeEnum;  
16 import cn.iocoder.yudao.module.infra.service.codegen.inner.CodegenBuilder; 15 import cn.iocoder.yudao.module.infra.service.codegen.inner.CodegenBuilder;
17 import cn.iocoder.yudao.module.infra.service.codegen.inner.CodegenEngine; 16 import cn.iocoder.yudao.module.infra.service.codegen.inner.CodegenEngine;
18 -import cn.iocoder.yudao.module.infra.service.codegen.inner.CodegenSQLParser;  
19 import cn.iocoder.yudao.module.infra.service.db.DatabaseTableService; 17 import cn.iocoder.yudao.module.infra.service.db.DatabaseTableService;
20 import cn.iocoder.yudao.module.system.api.user.AdminUserApi; 18 import cn.iocoder.yudao.module.system.api.user.AdminUserApi;
21 -import org.apache.commons.collections4.KeyValue; 19 +import com.baomidou.mybatisplus.generator.config.po.TableField;
  20 +import com.baomidou.mybatisplus.generator.config.po.TableInfo;
22 import org.springframework.stereotype.Service; 21 import org.springframework.stereotype.Service;
23 import org.springframework.transaction.annotation.Transactional; 22 import org.springframework.transaction.annotation.Transactional;
24 23
@@ -56,66 +55,48 @@ public class CodegenServiceImpl implements CodegenService { @@ -56,66 +55,48 @@ public class CodegenServiceImpl implements CodegenService {
56 @Resource 55 @Resource
57 private CodegenEngine codegenEngine; 56 private CodegenEngine codegenEngine;
58 57
59 - private Long createCodegen0(Long userId, CodegenImportTypeEnum importType,  
60 - DatabaseTableDO schemaTable, List<DatabaseColumnDO> schemaColumns) { 58 + @Override
  59 + @Transactional(rollbackFor = Exception.class)
  60 + public List<Long> createCodegenList(Long userId, CodegenCreateListReqVO reqVO) {
  61 + List<Long> ids = new ArrayList<>(reqVO.getTableNames().size());
  62 + // 遍历添加。虽然效率会低一点,但是没必要做成完全批量,因为不会这么大量
  63 + reqVO.getTableNames().forEach(tableName -> ids.add(createCodegen(userId, reqVO.getDataSourceConfigId(), tableName)));
  64 + return ids;
  65 + }
  66 +
  67 + public Long createCodegen(Long userId, Long dataSourceConfigId, String tableName) {
  68 + // 从数据库中,获得数据库表结构
  69 + TableInfo tableInfo = databaseTableService.getTable(dataSourceConfigId, tableName);
  70 + // 导入
  71 + return createCodegen0(userId, dataSourceConfigId, tableInfo);
  72 + }
  73 +
  74 + private Long createCodegen0(Long userId, Long dataSourceConfigId, TableInfo tableInfo) {
61 // 校验导入的表和字段非空 75 // 校验导入的表和字段非空
62 - if (schemaTable == null) { 76 + if (tableInfo == null) {
63 throw exception(CODEGEN_IMPORT_TABLE_NULL); 77 throw exception(CODEGEN_IMPORT_TABLE_NULL);
64 } 78 }
65 - if (CollUtil.isEmpty(schemaColumns)) { 79 + if (CollUtil.isEmpty(tableInfo.getFields())) {
66 throw exception(CODEGEN_IMPORT_COLUMNS_NULL); 80 throw exception(CODEGEN_IMPORT_COLUMNS_NULL);
67 } 81 }
68 // 校验是否已经存在 82 // 校验是否已经存在
69 - if (codegenTableMapper.selectByTableName(schemaTable.getTableName()) != null) { 83 + if (codegenTableMapper.selectByTableNameAndDataSourceConfigId(tableInfo.getName(),
  84 + dataSourceConfigId) != null) {
70 throw exception(CODEGEN_TABLE_EXISTS); 85 throw exception(CODEGEN_TABLE_EXISTS);
71 } 86 }
72 87
73 // 构建 CodegenTableDO 对象,插入到 DB 中 88 // 构建 CodegenTableDO 对象,插入到 DB 中
74 - CodegenTableDO table = codegenBuilder.buildTable(schemaTable);  
75 - table.setImportType(importType.getType()); 89 + CodegenTableDO table = codegenBuilder.buildTable(tableInfo);
  90 + table.setDataSourceConfigId(dataSourceConfigId);
76 table.setAuthor(userApi.getUser(userId).getNickname()); 91 table.setAuthor(userApi.getUser(userId).getNickname());
77 codegenTableMapper.insert(table); 92 codegenTableMapper.insert(table);
78 // 构建 CodegenColumnDO 数组,插入到 DB 中 93 // 构建 CodegenColumnDO 数组,插入到 DB 中
79 - List<CodegenColumnDO> columns = codegenBuilder.buildColumns(table.getId(), schemaColumns); 94 + List<CodegenColumnDO> columns = codegenBuilder.buildColumns(table.getId(), tableInfo.getFields());
80 codegenColumnMapper.insertBatch(columns); 95 codegenColumnMapper.insertBatch(columns);
81 return table.getId(); 96 return table.getId();
82 } 97 }
83 98
84 @Override 99 @Override
85 - public Long createCodegenListFromSQL(Long userId, String sql) {  
86 - // 从 SQL 中,获得数据库表结构  
87 - DatabaseTableDO schemaTable;  
88 - List<DatabaseColumnDO> schemaColumns;  
89 - try {  
90 - KeyValue<DatabaseTableDO, List<DatabaseColumnDO>> result = CodegenSQLParser.parse(sql);  
91 - schemaTable = result.getKey();  
92 - schemaColumns = result.getValue();  
93 - } catch (Exception ex) {  
94 - throw exception(CODEGEN_PARSE_SQL_ERROR);  
95 - }  
96 - // 导入  
97 - return this.createCodegen0(userId, CodegenImportTypeEnum.SQL, schemaTable, schemaColumns);  
98 - }  
99 -  
100 - @Override  
101 - public Long createCodegen(Long userId, String tableName) {  
102 - // 从数据库中,获得数据库表结构  
103 - DatabaseTableDO schemaTable = databaseTableService.getTable(9L, tableName);  
104 - List<DatabaseColumnDO> schemaColumns = databaseTableService.getColumnList(9L, tableName);  
105 - // 导入  
106 - return this.createCodegen0(userId, CodegenImportTypeEnum.DB, schemaTable, schemaColumns);  
107 - }  
108 -  
109 - @Override  
110 - @Transactional(rollbackFor = Exception.class)  
111 - public List<Long> createCodegenListFromDB(Long userId, List<String> tableNames) {  
112 - List<Long> ids = new ArrayList<>(tableNames.size());  
113 - // 遍历添加。虽然效率会低一点,但是没必要做成完全批量,因为不会这么大量  
114 - tableNames.forEach(tableName -> ids.add(createCodegen(userId, tableName)));  
115 - return ids;  
116 - }  
117 -  
118 - @Override  
119 @Transactional(rollbackFor = Exception.class) 100 @Transactional(rollbackFor = Exception.class)
120 public void updateCodegen(CodegenUpdateReqVO updateReqVO) { 101 public void updateCodegen(CodegenUpdateReqVO updateReqVO) {
121 // 校验是否已经存在 102 // 校验是否已经存在
@@ -140,54 +121,33 @@ public class CodegenServiceImpl implements CodegenService { @@ -140,54 +121,33 @@ public class CodegenServiceImpl implements CodegenService {
140 throw exception(CODEGEN_TABLE_NOT_EXISTS); 121 throw exception(CODEGEN_TABLE_NOT_EXISTS);
141 } 122 }
142 // 从数据库中,获得数据库表结构 123 // 从数据库中,获得数据库表结构
143 - List<DatabaseColumnDO> schemaColumns = databaseTableService.getColumnList(0L, table.getTableName());  
144 - 124 + TableInfo tableInfo = databaseTableService.getTable(table.getDataSourceConfigId(), table.getTableName());
145 // 执行同步 125 // 执行同步
146 - this.syncCodegen0(tableId, schemaColumns); 126 + syncCodegen0(tableId, tableInfo);
147 } 127 }
148 128
149 - @Override  
150 - @Transactional(rollbackFor = Exception.class)  
151 - public void syncCodegenFromSQL(Long tableId, String sql) {  
152 - // 校验是否已经存在  
153 - CodegenTableDO table = codegenTableMapper.selectById(tableId);  
154 - if (table == null) {  
155 - throw exception(CODEGEN_TABLE_NOT_EXISTS);  
156 - }  
157 - // 从 SQL 中,获得数据库表结构  
158 - List<DatabaseColumnDO> schemaColumns;  
159 - try {  
160 - KeyValue<DatabaseTableDO, List<DatabaseColumnDO>> result = CodegenSQLParser.parse(sql);  
161 - schemaColumns = result.getValue();  
162 - } catch (Exception ex) {  
163 - throw exception(CODEGEN_PARSE_SQL_ERROR);  
164 - }  
165 -  
166 - // 执行同步  
167 - this.syncCodegen0(tableId, schemaColumns);  
168 - }  
169 -  
170 - private void syncCodegen0(Long tableId, List<DatabaseColumnDO> schemaColumns) { 129 + private void syncCodegen0(Long tableId, TableInfo tableInfo) {
171 // 校验导入的字段不为空 130 // 校验导入的字段不为空
172 - if (CollUtil.isEmpty(schemaColumns)) { 131 + List<TableField> tableFields = tableInfo.getFields();
  132 + if (CollUtil.isEmpty(tableFields)) {
173 throw exception(CODEGEN_SYNC_COLUMNS_NULL); 133 throw exception(CODEGEN_SYNC_COLUMNS_NULL);
174 } 134 }
175 - Set<String> schemaColumnNames = CollectionUtils.convertSet(schemaColumns, DatabaseColumnDO::getColumnName); 135 + Set<String> tableFieldNames = CollectionUtils.convertSet(tableFields, TableField::getName);
176 136
177 // 构建 CodegenColumnDO 数组,只同步新增的字段 137 // 构建 CodegenColumnDO 数组,只同步新增的字段
178 List<CodegenColumnDO> codegenColumns = codegenColumnMapper.selectListByTableId(tableId); 138 List<CodegenColumnDO> codegenColumns = codegenColumnMapper.selectListByTableId(tableId);
179 Set<String> codegenColumnNames = CollectionUtils.convertSet(codegenColumns, CodegenColumnDO::getColumnName); 139 Set<String> codegenColumnNames = CollectionUtils.convertSet(codegenColumns, CodegenColumnDO::getColumnName);
180 // 移除已经存在的字段 140 // 移除已经存在的字段
181 - schemaColumns.removeIf(column -> codegenColumnNames.contains(column.getColumnName())); 141 + tableFields.removeIf(column -> codegenColumnNames.contains(column.getColumnName()));
182 // 计算需要删除的字段 142 // 计算需要删除的字段
183 - Set<Long> deleteColumnIds = codegenColumns.stream().filter(column -> !schemaColumnNames.contains(column.getColumnName())) 143 + Set<Long> deleteColumnIds = codegenColumns.stream().filter(column -> !tableFieldNames.contains(column.getColumnName()))
184 .map(CodegenColumnDO::getId).collect(Collectors.toSet()); 144 .map(CodegenColumnDO::getId).collect(Collectors.toSet());
185 - if (CollUtil.isEmpty(schemaColumns) && CollUtil.isEmpty(deleteColumnIds)) { 145 + if (CollUtil.isEmpty(tableFields) && CollUtil.isEmpty(deleteColumnIds)) {
186 throw exception(CODEGEN_SYNC_NONE_CHANGE); 146 throw exception(CODEGEN_SYNC_NONE_CHANGE);
187 } 147 }
188 148
189 // 插入新增的字段 149 // 插入新增的字段
190 - List<CodegenColumnDO> columns = codegenBuilder.buildColumns(tableId, schemaColumns); 150 + List<CodegenColumnDO> columns = codegenBuilder.buildColumns(tableId, tableFields);
191 codegenColumnMapper.insertBatch(columns); 151 codegenColumnMapper.insertBatch(columns);
192 // 删除不存在的字段 152 // 删除不存在的字段
193 if (CollUtil.isNotEmpty(deleteColumnIds)) { 153 if (CollUtil.isNotEmpty(deleteColumnIds)) {
@@ -220,11 +180,6 @@ public class CodegenServiceImpl implements CodegenService { @@ -220,11 +180,6 @@ public class CodegenServiceImpl implements CodegenService {
220 } 180 }
221 181
222 @Override 182 @Override
223 - public List<CodegenTableDO> getCodeGenTableList() {  
224 - return codegenTableMapper.selectList();  
225 - }  
226 -  
227 - @Override  
228 public List<CodegenColumnDO> getCodegenColumnListByTableId(Long tableId) { 183 public List<CodegenColumnDO> getCodegenColumnListByTableId(Long tableId) {
229 return codegenColumnMapper.selectListByTableId(tableId); 184 return codegenColumnMapper.selectListByTableId(tableId);
230 } 185 }
@@ -246,13 +201,18 @@ public class CodegenServiceImpl implements CodegenService { @@ -246,13 +201,18 @@ public class CodegenServiceImpl implements CodegenService {
246 } 201 }
247 202
248 @Override 203 @Override
249 - public List<DatabaseTableDO> getSchemaTableList(Long dataSourceConfigId, String tableName, String tableComment) {  
250 - List<DatabaseTableDO> tables = databaseTableService.getTableList(dataSourceConfigId, tableName, tableComment);  
251 - // TODO 强制移除 Quartz 的表,未来做成可配置  
252 - tables.removeIf(table -> table.getTableName().startsWith("QRTZ_"));  
253 - tables.removeIf(table -> table.getTableName().startsWith("ACT_"));  
254 - tables.removeIf(table -> table.getTableName().startsWith("FLW_"));  
255 - return tables; 204 + public List<DatabaseTableRespVO> getDatabaseTableList(Long dataSourceConfigId, String name, String comment) {
  205 + List<TableInfo> tables = databaseTableService.getTableList(dataSourceConfigId, name, comment);
  206 + // 移除置顶前缀的表名 // TODO 未来做成可配置
  207 + tables.removeIf(table -> table.getName().startsWith("QRTZ_"));
  208 + tables.removeIf(table -> table.getName().startsWith("ACT_"));
  209 + tables.removeIf(table -> table.getName().startsWith("FLW_"));
  210 + // 移除已经生成的表
  211 + // 移除在 Codegen 中,已经存在的
  212 + Set<String> existsTables = CollectionUtils.convertSet(
  213 + codegenTableMapper.selectListByDataSourceConfigId(dataSourceConfigId), CodegenTableDO::getTableName);
  214 + tables.removeIf(table -> existsTables.contains(table.getName()));
  215 + return CodegenConvert.INSTANCE.convertList04(tables);
256 } 216 }
257 217
258 } 218 }
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/inner/CodegenBuilder.java
@@ -7,23 +7,22 @@ import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO; @@ -7,23 +7,22 @@ import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
7 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert; 7 import cn.iocoder.yudao.module.infra.convert.codegen.CodegenConvert;
8 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO; 8 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenColumnDO;
9 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO; 9 import cn.iocoder.yudao.module.infra.dal.dataobject.codegen.CodegenTableDO;
10 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
11 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
12 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenColumnHtmlTypeEnum; 10 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenColumnHtmlTypeEnum;
13 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenColumnListConditionEnum; 11 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenColumnListConditionEnum;
14 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenTemplateTypeEnum; 12 import cn.iocoder.yudao.module.infra.enums.codegen.CodegenTemplateTypeEnum;
  13 +import com.baomidou.mybatisplus.generator.config.po.TableField;
  14 +import com.baomidou.mybatisplus.generator.config.po.TableInfo;
15 import com.google.common.collect.Sets; 15 import com.google.common.collect.Sets;
16 import org.springframework.stereotype.Component; 16 import org.springframework.stereotype.Component;
17 17
18 -import java.math.BigDecimal;  
19 import java.util.*; 18 import java.util.*;
20 19
21 import static cn.hutool.core.text.CharSequenceUtil.*; 20 import static cn.hutool.core.text.CharSequenceUtil.*;
22 21
23 /** 22 /**
24 * 代码生成器的 Builder,负责: 23 * 代码生成器的 Builder,负责:
25 - * 1. 将数据库的表 {@link DatabaseTableDO} 定义,构建成 {@link CodegenTableDO}  
26 - * 2. 将数据库的列 {@link DatabaseColumnDO} 构定义,建成 {@link CodegenColumnDO} 24 + * 1. 将数据库的表 {@link TableInfo} 定义,构建成 {@link CodegenTableDO}
  25 + * 2. 将数据库的列 {@link TableField} 构定义,建成 {@link CodegenColumnDO}
27 */ 26 */
28 @Component 27 @Component
29 public class CodegenBuilder { 28 public class CodegenBuilder {
@@ -82,24 +81,6 @@ public class CodegenBuilder { @@ -82,24 +81,6 @@ public class CodegenBuilder {
82 */ 81 */
83 private static final Set<String> LIST_OPERATION_RESULT_EXCLUDE_COLUMN = Sets.newHashSet(); 82 private static final Set<String> LIST_OPERATION_RESULT_EXCLUDE_COLUMN = Sets.newHashSet();
84 83
85 - /**  
86 - * Java 类型与 MySQL 类型的映射关系  
87 - */  
88 - private static final Map<String, Set<String>> javaTypeMappings = MapUtil.<String, Set<String>>builder()  
89 - .put(Boolean.class.getSimpleName(), Sets.newHashSet("bit"))  
90 - .put(Integer.class.getSimpleName(), Sets.newHashSet(  
91 - "tinyint", "smallint", "mediumint", "int", "integer"))  
92 - .put(Long.class.getSimpleName(), Sets.newHashSet("bigint", "number"))  
93 - .put(Double.class.getSimpleName(), Sets.newHashSet("float", "double"))  
94 - .put(BigDecimal.class.getSimpleName(), Sets.newHashSet("decimal", "numeric"))  
95 - .put(String.class.getSimpleName(), Sets.newHashSet(  
96 - "tinytext", "text", "mediumtext", "longtext", "nclob", // 长文本  
97 - "char", "varchar", "nvarchar", "varchar2", "nvarchar2", // 短文本  
98 - "json")) // 特殊文本  
99 - .put(Date.class.getSimpleName(), Sets.newHashSet("datetime", "time", "date", "timestamp"))  
100 - .put("byte[]", Sets.newHashSet("blob"))  
101 - .build();  
102 -  
103 static { 84 static {
104 Arrays.stream(ReflectUtil.getFields(BaseDO.class)).forEach(field -> BASE_DO_FIELDS.add(field.getName())); 85 Arrays.stream(ReflectUtil.getFields(BaseDO.class)).forEach(field -> BASE_DO_FIELDS.add(field.getName()));
105 BASE_DO_FIELDS.add(TENANT_ID_FIELD); 86 BASE_DO_FIELDS.add(TENANT_ID_FIELD);
@@ -112,8 +93,8 @@ public class CodegenBuilder { @@ -112,8 +93,8 @@ public class CodegenBuilder {
112 LIST_OPERATION_RESULT_EXCLUDE_COLUMN.remove("createTime"); // 创建时间,还是需要返回的 93 LIST_OPERATION_RESULT_EXCLUDE_COLUMN.remove("createTime"); // 创建时间,还是需要返回的
113 } 94 }
114 95
115 - public CodegenTableDO buildTable(DatabaseTableDO schemaTable) {  
116 - CodegenTableDO table = CodegenConvert.INSTANCE.convert(schemaTable); 96 + public CodegenTableDO buildTable(TableInfo tableInfo) {
  97 + CodegenTableDO table = CodegenConvert.INSTANCE.convert(tableInfo);
117 initTableDefault(table); 98 initTableDefault(table);
118 return table; 99 return table;
119 } 100 }
@@ -136,43 +117,19 @@ public class CodegenBuilder { @@ -136,43 +117,19 @@ public class CodegenBuilder {
136 table.setTemplateType(CodegenTemplateTypeEnum.CRUD.getType()); 117 table.setTemplateType(CodegenTemplateTypeEnum.CRUD.getType());
137 } 118 }
138 119
139 - public List<CodegenColumnDO> buildColumns(Long tableId, List<DatabaseColumnDO> schemaColumns) {  
140 - List<CodegenColumnDO> columns = CodegenConvert.INSTANCE.convertList(schemaColumns); 120 + public List<CodegenColumnDO> buildColumns(Long tableId, List<TableField> tableFields) {
  121 + List<CodegenColumnDO> columns = CodegenConvert.INSTANCE.convertList(tableFields);
  122 + int index = 1;
141 for (CodegenColumnDO column : columns) { 123 for (CodegenColumnDO column : columns) {
142 column.setTableId(tableId); 124 column.setTableId(tableId);
143 - initColumnDefault(column); 125 + column.setOrdinalPosition(index++);
  126 + // 初始化 Column 列的默认字段
  127 + processColumnOperation(column); // 处理 CRUD 相关的字段的默认值
  128 + processColumnUI(column); // 处理 UI 相关的字段的默认值
144 } 129 }
145 return columns; 130 return columns;
146 } 131 }
147 132
148 - /**  
149 - * 初始化 Column 列的默认字段  
150 - *  
151 - * @param column 列定义  
152 - */  
153 - private void initColumnDefault(CodegenColumnDO column) {  
154 - // 处理 Java 相关的字段的默认值  
155 - processColumnJava(column);  
156 - // 处理 CRUD 相关的字段的默认值  
157 - processColumnOperation(column);  
158 - // 处理 UI 相关的字段的默认值  
159 - processColumnUI(column);  
160 - }  
161 -  
162 - private void processColumnJava(CodegenColumnDO column) {  
163 - // 处理 javaField 字段  
164 - column.setJavaField(toCamelCase(column.getColumnName()));  
165 - // 处理 dataType 字段  
166 - String dataType = column.getDataType().toLowerCase();  
167 - javaTypeMappings.entrySet().stream()  
168 - .filter(entry -> entry.getValue().contains(dataType))  
169 - .findFirst().ifPresent(entry -> column.setJavaType(entry.getKey()));  
170 - if (column.getJavaType() == null) {  
171 - throw new IllegalStateException(String.format("column(%s) 的数据库类型(%s) 找不到匹配的 Java 类型",  
172 - column.getColumnName(), column.getJavaType()));  
173 - }  
174 - }  
175 -  
176 private void processColumnOperation(CodegenColumnDO column) { 133 private void processColumnOperation(CodegenColumnDO column) {
177 // 处理 createOperation 字段 134 // 处理 createOperation 字段
178 column.setCreateOperation(!CREATE_OPERATION_EXCLUDE_COLUMN.contains(column.getJavaField()) 135 column.setCreateOperation(!CREATE_OPERATION_EXCLUDE_COLUMN.contains(column.getJavaField())
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/inner/CodegenSQLParser.java deleted
1 -package cn.iocoder.yudao.module.infra.service.codegen.inner;  
2 -  
3 -import cn.hutool.core.collection.CollUtil;  
4 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
5 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
6 -import com.alibaba.druid.DbType;  
7 -import com.alibaba.druid.sql.ast.expr.SQLCharExpr;  
8 -import com.alibaba.druid.sql.ast.statement.SQLColumnDefinition;  
9 -import com.alibaba.druid.sql.ast.statement.SQLCreateTableStatement;  
10 -import com.alibaba.druid.sql.ast.statement.SQLPrimaryKey;  
11 -import com.alibaba.druid.sql.ast.statement.SQLTableElement;  
12 -import com.alibaba.druid.sql.dialect.mysql.ast.statement.MySqlCreateTableStatement;  
13 -import com.alibaba.druid.sql.repository.SchemaRepository;  
14 -import org.apache.commons.collections4.KeyValue;  
15 -import org.apache.commons.collections4.keyvalue.DefaultKeyValue;  
16 -  
17 -import java.util.ArrayList;  
18 -import java.util.List;  
19 -import java.util.Objects;  
20 -  
21 -import static com.alibaba.druid.sql.SQLUtils.normalize;  
22 -  
23 -/**  
24 - * SQL 解析器,将创建表的 SQL,解析成 {@link DatabaseTableDO} 和 {@link DatabaseColumnDO} 对象,  
25 - * 后续可以基于它们,生成代码~  
26 - *  
27 - * @author 芋道源码  
28 - */  
29 -public class CodegenSQLParser {  
30 -  
31 - /**  
32 - * 解析建表 SQL 语句,返回 {@link DatabaseTableDO} 和 {@link DatabaseColumnDO} 对象  
33 - *  
34 - * @param sql 建表 SQL 语句  
35 - * @return 解析结果  
36 - */  
37 - public static KeyValue<DatabaseTableDO, List<DatabaseColumnDO>> parse(String sql) {  
38 - // 解析 SQL 成 Statement  
39 - SQLCreateTableStatement statement = parseCreateSQL(sql);  
40 - // 解析 Table 表  
41 - DatabaseTableDO table = parseTable(statement);  
42 - // 解析 Column 字段  
43 - List<DatabaseColumnDO> columns = parseColumns(statement);  
44 - columns.forEach(column -> column.setTableName(table.getTableName()));  
45 - // 返回  
46 - return new DefaultKeyValue<>(table, columns);  
47 - }  
48 -  
49 - /**  
50 - * 使用 Druid 工具,建表 SQL 语句  
51 - *  
52 - * @param sql 建表 SQL 语句  
53 - * @return 创建 Statement  
54 - */  
55 - private static SQLCreateTableStatement parseCreateSQL(String sql) {  
56 - // 解析 SQL  
57 - SchemaRepository repository = new SchemaRepository(DbType.mysql);  
58 - repository.console(sql);  
59 - // 获得该表对应的 MySqlCreateTableStatement 对象  
60 - String tableName = CollUtil.getFirst(repository.getDefaultSchema().getObjects()).getName();  
61 - return (MySqlCreateTableStatement) repository.findTable(tableName).getStatement();  
62 - }  
63 -  
64 - private static DatabaseTableDO parseTable(SQLCreateTableStatement statement) {  
65 - return DatabaseTableDO.builder()  
66 - .tableName(statement.getTableSource().getTableName(true))  
67 - .tableComment(getCommentText(statement))  
68 - .build();  
69 - }  
70 -  
71 - private static String getCommentText(SQLCreateTableStatement statement) {  
72 - if (statement == null || statement.getComment() == null) {  
73 - return "";  
74 - }  
75 - return ((SQLCharExpr) statement.getComment()).getText();  
76 - }  
77 -  
78 - private static List<DatabaseColumnDO> parseColumns(SQLCreateTableStatement statement) {  
79 - List<DatabaseColumnDO> columns = new ArrayList<>();  
80 - statement.getTableElementList().forEach(element -> parseColumn(columns, element));  
81 - return columns;  
82 - }  
83 -  
84 - private static void parseColumn(List<DatabaseColumnDO> columns, SQLTableElement element) {  
85 - // 处理主键  
86 - if (element instanceof SQLPrimaryKey) {  
87 - parsePrimaryKey(columns, (SQLPrimaryKey) element);  
88 - return;  
89 - }  
90 - // 处理字段定义  
91 - if (element instanceof SQLColumnDefinition) {  
92 - parseColumnDefinition(columns, (SQLColumnDefinition) element);  
93 - }  
94 - }  
95 -  
96 - private static void parsePrimaryKey(List<DatabaseColumnDO> columns, SQLPrimaryKey primaryKey) {  
97 - String columnName = normalize(primaryKey.getColumns().get(0).toString()); // 暂时不考虑联合主键  
98 - // 匹配 columns 主键字段,设置为 primary  
99 - columns.stream().filter(column -> column.getColumnName().equals(columnName))  
100 - .forEach(column -> column.setPrimaryKey(true));  
101 - }  
102 -  
103 - private static void parseColumnDefinition(List<DatabaseColumnDO> columns, SQLColumnDefinition definition) {  
104 - String text = definition.toString().toUpperCase();  
105 - columns.add(DatabaseColumnDO.builder()  
106 - .columnName(normalize(definition.getColumnName()))  
107 - .dataType(definition.getDataType().toString())  
108 - .columnComment(Objects.isNull(definition.getComment()) ? ""  
109 - : normalize(definition.getComment().toString()))  
110 - .nullable(!text.contains(" NOT NULL"))  
111 - .primaryKey(false)  
112 - .autoIncrement(text.contains("AUTO_INCREMENT"))  
113 - .ordinalPosition(columns.size() + 1)  
114 - .build());  
115 - }  
116 -  
117 -}  
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigService.java
@@ -3,7 +3,6 @@ package cn.iocoder.yudao.module.infra.service.db; @@ -3,7 +3,6 @@ package cn.iocoder.yudao.module.infra.service.db;
3 import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigCreateReqVO; 3 import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigCreateReqVO;
4 import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigUpdateReqVO; 4 import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigUpdateReqVO;
5 import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO; 5 import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO;
6 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
7 6
8 import javax.validation.Valid; 7 import javax.validation.Valid;
9 import java.util.List; 8 import java.util.List;
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableService.java
1 package cn.iocoder.yudao.module.infra.service.db; 1 package cn.iocoder.yudao.module.infra.service.db;
2 2
3 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
4 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
5 import com.baomidou.mybatisplus.generator.config.po.TableInfo; 3 import com.baomidou.mybatisplus.generator.config.po.TableInfo;
6 4
7 import java.util.List; 5 import java.util.List;
@@ -17,11 +15,11 @@ public interface DatabaseTableService { @@ -17,11 +15,11 @@ public interface DatabaseTableService {
17 * 获得表列表,基于表名称 + 表描述进行模糊匹配 15 * 获得表列表,基于表名称 + 表描述进行模糊匹配
18 * 16 *
19 * @param dataSourceConfigId 数据源配置的编号 17 * @param dataSourceConfigId 数据源配置的编号
20 - * @param tableNameLike 表名称,模糊匹配  
21 - * @param tableCommentLike 表描述,模糊匹配 18 + * @param nameLike 表名称,模糊匹配
  19 + * @param commentLike 表描述,模糊匹配
22 * @return 表列表 20 * @return 表列表
23 */ 21 */
24 - List<DatabaseTableDO> getTableList(Long dataSourceConfigId, String tableNameLike, String tableCommentLike); 22 + List<TableInfo> getTableList(Long dataSourceConfigId, String nameLike, String commentLike);
25 23
26 /** 24 /**
27 * 获得指定表名 25 * 获得指定表名
@@ -30,35 +28,6 @@ public interface DatabaseTableService { @@ -30,35 +28,6 @@ public interface DatabaseTableService {
30 * @param tableName 表名称 28 * @param tableName 表名称
31 * @return 表 29 * @return 表
32 */ 30 */
33 - DatabaseTableDO getTable(Long dataSourceConfigId, String tableName);  
34 -  
35 - /**  
36 - * 获得指定表的字段列表  
37 - *  
38 - * @param dataSourceConfigId 数据源配置的编号  
39 - * @param tableName 表名称  
40 - * @return 字段列表  
41 - */  
42 - List<DatabaseColumnDO> getColumnList(Long dataSourceConfigId, String tableName);  
43 -  
44 -  
45 - /**  
46 - * 获得表列表,基于表名称 + 表描述进行模糊匹配  
47 - *  
48 - * @param dataSourceConfigId 数据源配置的编号  
49 - * @param tableNameLike 表名称,模糊匹配  
50 - * @param tableCommentLike 表描述,模糊匹配  
51 - * @return 表列表  
52 - */  
53 - List<TableInfo> getTableList2(Long dataSourceConfigId, String tableNameLike, String tableCommentLike);  
54 -  
55 - /**  
56 - * 获得指定表名  
57 - *  
58 - * @param dataSourceConfigId 数据源配置的编号  
59 - * @param tableName 表名称  
60 - * @return 表  
61 - */  
62 - TableInfo getTable2(Long dataSourceConfigId, String tableName); 31 + TableInfo getTable(Long dataSourceConfigId, String tableName);
63 32
64 } 33 }
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImpl.java
@@ -2,20 +2,20 @@ package cn.iocoder.yudao.module.infra.service.db; @@ -2,20 +2,20 @@ package cn.iocoder.yudao.module.infra.service.db;
2 2
3 import cn.hutool.core.collection.CollUtil; 3 import cn.hutool.core.collection.CollUtil;
4 import cn.hutool.core.lang.Assert; 4 import cn.hutool.core.lang.Assert;
5 -import cn.iocoder.yudao.framework.mybatis.core.util.JdbcUtils; 5 +import cn.hutool.core.util.StrUtil;
6 import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO; 6 import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO;
7 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseColumnDO;  
8 -import cn.iocoder.yudao.module.infra.dal.dataobject.db.DatabaseTableDO;  
9 -import cn.iocoder.yudao.module.infra.dal.mysql.db.DatabaseTableDAO;  
10 -import com.baomidou.mybatisplus.annotation.DbType; 7 +import com.baomidou.mybatisplus.generator.config.DataSourceConfig;
  8 +import com.baomidou.mybatisplus.generator.config.GlobalConfig;
  9 +import com.baomidou.mybatisplus.generator.config.StrategyConfig;
  10 +import com.baomidou.mybatisplus.generator.config.builder.ConfigBuilder;
11 import com.baomidou.mybatisplus.generator.config.po.TableInfo; 11 import com.baomidou.mybatisplus.generator.config.po.TableInfo;
12 -import lombok.SneakyThrows; 12 +import com.baomidou.mybatisplus.generator.config.rules.DateType;
13 import org.springframework.stereotype.Service; 13 import org.springframework.stereotype.Service;
14 14
15 import javax.annotation.Resource; 15 import javax.annotation.Resource;
16 -import java.sql.Connection;  
17 import java.util.Comparator; 16 import java.util.Comparator;
18 import java.util.List; 17 import java.util.List;
  18 +import java.util.stream.Collectors;
19 19
20 /** 20 /**
21 * 数据库表 Service 实现类 21 * 数据库表 Service 实现类
@@ -28,61 +28,38 @@ public class DatabaseTableServiceImpl implements DatabaseTableService { @@ -28,61 +28,38 @@ public class DatabaseTableServiceImpl implements DatabaseTableService {
28 @Resource 28 @Resource
29 private DataSourceConfigService dataSourceConfigService; 29 private DataSourceConfigService dataSourceConfigService;
30 30
31 - @Resource  
32 - private List<DatabaseTableDAO> databaseTableDAOs;  
33 -  
34 - @Override  
35 - @SneakyThrows  
36 - public List<DatabaseTableDO> getTableList(Long dataSourceConfigId, String tableNameLike, String tableCommentLike) {  
37 - try (Connection connection = getConnection(dataSourceConfigId)) {  
38 - return getDatabaseTableDAO(dataSourceConfigId).selectTableList(connection, tableNameLike, tableCommentLike);  
39 - }  
40 - }  
41 -  
42 - @Override  
43 - @SneakyThrows  
44 - public DatabaseTableDO getTable(Long dataSourceConfigId, String tableName) {  
45 - try (Connection connection = getConnection(dataSourceConfigId)) {  
46 - return getDatabaseTableDAO(dataSourceConfigId).selectTable(connection, tableName);  
47 - }  
48 - }  
49 -  
50 - @Override  
51 - @SneakyThrows  
52 - public List<DatabaseColumnDO> getColumnList(Long dataSourceConfigId, String tableName) {  
53 - try (Connection connection = getConnection(dataSourceConfigId)) {  
54 - List<DatabaseColumnDO> columns = getDatabaseTableDAO(dataSourceConfigId).selectColumnList(connection, tableName);  
55 - columns.sort(Comparator.comparing(DatabaseColumnDO::getOrdinalPosition));  
56 - return columns;  
57 - }  
58 - }  
59 -  
60 @Override 31 @Override
61 - public List<TableInfo> getTableList2(Long dataSourceConfigId, String tableNameLike, String tableCommentLike) {  
62 - return null; 32 + public List<TableInfo> getTableList(Long dataSourceConfigId, String nameLike, String commentLike) {
  33 + List<TableInfo> tables = getTableList0(dataSourceConfigId, null);
  34 + return tables.stream().filter(tableInfo -> (StrUtil.isEmpty(nameLike) || tableInfo.getName().contains(nameLike))
  35 + && (StrUtil.isEmpty(commentLike) || tableInfo.getComment().contains(commentLike)))
  36 + .collect(Collectors.toList());
63 } 37 }
64 38
65 @Override 39 @Override
66 - public TableInfo getTable2(Long dataSourceConfigId, String tableName) {  
67 - return null; 40 + public TableInfo getTable(Long dataSourceConfigId, String name) {
  41 + return CollUtil.getFirst(getTableList0(dataSourceConfigId, name));
68 } 42 }
69 43
70 - private Connection getConnection(Long dataSourceConfigId) { 44 + public List<TableInfo> getTableList0(Long dataSourceConfigId, String name) {
  45 + // 获得数据源配置
71 DataSourceConfigDO config = dataSourceConfigService.getDataSourceConfig(dataSourceConfigId); 46 DataSourceConfigDO config = dataSourceConfigService.getDataSourceConfig(dataSourceConfigId);
72 Assert.notNull(config, "数据源({}) 不存在!", dataSourceConfigId); 47 Assert.notNull(config, "数据源({}) 不存在!", dataSourceConfigId);
73 - return JdbcUtils.getConnection(config.getUrl(), config.getUsername(), config.getPassword());  
74 - }  
75 48
76 - private DatabaseTableDAO getDatabaseTableDAO(Long dataSourceConfigId) {  
77 - DataSourceConfigDO config = dataSourceConfigService.getDataSourceConfig(dataSourceConfigId);  
78 - Assert.notNull(config, "数据源({}) 不存在!", dataSourceConfigId);  
79 - // 获得 dbType  
80 - DbType dbType = JdbcUtils.getDbType(config.getUrl());  
81 - Assert.notNull(config, "数据源类型({}) 不存在!", config.getUrl());  
82 - // 获得 DatabaseTableDAO  
83 - DatabaseTableDAO dao = CollUtil.findOne(databaseTableDAOs, databaseTableDAO -> databaseTableDAO.getType().equals(dbType));  
84 - Assert.notNull(dao, "DAO({}) 查找不到实现!", dbType);  
85 - return dao; 49 + // 使用 MyBatis Plus Generator 解析表结构
  50 + DataSourceConfig dataSourceConfig = new DataSourceConfig.Builder(config.getUrl(), config.getUsername(),
  51 + config.getPassword()).build();
  52 + StrategyConfig.Builder strategyConfig = new StrategyConfig.Builder();
  53 + if (StrUtil.isNotEmpty(name)) {
  54 + strategyConfig.addInclude(name);
  55 + }
  56 + GlobalConfig globalConfig = new GlobalConfig.Builder().dateType(DateType.ONLY_DATE).build(); // 只使用 Date 类型,不使用 LocalDate
  57 + ConfigBuilder builder = new ConfigBuilder(null, dataSourceConfig, strategyConfig.build(),
  58 + null, globalConfig, null);
  59 + // 按照名字排序
  60 + List<TableInfo> tables = builder.getTableInfoList();
  61 + tables.sort(Comparator.comparing(TableInfo::getName));
  62 + return tables;
86 } 63 }
87 64
88 } 65 }
yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/DefaultDatabaseQueryTest.java 0 → 100644
  1 +package cn.iocoder.yudao.module.infra.service;
  2 +
  3 +import com.baomidou.mybatisplus.generator.IDatabaseQuery.DefaultDatabaseQuery;
  4 +import com.baomidou.mybatisplus.generator.config.DataSourceConfig;
  5 +import com.baomidou.mybatisplus.generator.config.builder.ConfigBuilder;
  6 +import com.baomidou.mybatisplus.generator.config.po.TableInfo;
  7 +
  8 +import java.util.List;
  9 +
  10 +public class DefaultDatabaseQueryTest {
  11 +
  12 + public static void main(String[] args) {
  13 + DataSourceConfig dataSourceConfig = new DataSourceConfig.Builder("jdbc:oracle:thin:@127.0.0.1:1521:xe",
  14 + "root", "123456").build();
  15 +// StrategyConfig strategyConfig = new StrategyConfig.Builder().build();
  16 +
  17 + ConfigBuilder builder = new ConfigBuilder(null, dataSourceConfig, null, null, null, null);
  18 +
  19 + DefaultDatabaseQuery query = new DefaultDatabaseQuery(builder);
  20 +
  21 + long time = System.currentTimeMillis();
  22 + List<TableInfo> tableInfos = query.queryTables();
  23 + System.out.println(tableInfos.size());
  24 + System.out.println(System.currentTimeMillis() - time);
  25 + }
  26 +
  27 +}
yudao-ui-admin/src/api/infra/codegen.js
@@ -73,26 +73,11 @@ export function getSchemaTableList(query) { @@ -73,26 +73,11 @@ export function getSchemaTableList(query) {
73 } 73 }
74 74
75 // 基于数据库的表结构,创建代码生成器的表定义 75 // 基于数据库的表结构,创建代码生成器的表定义
76 -export function createCodegenListFromDB(tableNames) { 76 +export function createCodegenList(data) {
77 return request({ 77 return request({
78 - url: '/infra/codegen/create-list-from-db', 78 + url: '/infra/codegen/create-list',
79 method: 'post', 79 method: 'post',
80 - headers:{  
81 - 'Content-type': 'application/x-www-form-urlencoded'  
82 - },  
83 - data: 'tableNames=' + tableNames  
84 - })  
85 -}  
86 -  
87 -// 基于 SQL 建表语句,创建代码生成器的表定义  
88 -export function createCodegenListFromSQL(data) {  
89 - return request({  
90 - url: '/infra/codegen/create-list-from-sql',  
91 - method: 'post',  
92 - headers:{  
93 - 'Content-type': 'application/x-www-form-urlencoded'  
94 - },  
95 - data: 'sql=' + data.sql, 80 + data: data
96 }) 81 })
97 } 82 }
98 83
yudao-ui-admin/src/views/infra/codegen/editTable.vue
@@ -19,7 +19,7 @@ @@ -19,7 +19,7 @@
19 </el-table-column> 19 </el-table-column>
20 <el-table-column 20 <el-table-column
21 label="物理类型" 21 label="物理类型"
22 - prop="dateType" 22 + prop="dataType"
23 min-width="10%" 23 min-width="10%"
24 :show-overflow-tooltip="true" 24 :show-overflow-tooltip="true"
25 /> 25 />
yudao-ui-admin/src/views/infra/codegen/importTable.vue
@@ -8,11 +8,11 @@ @@ -8,11 +8,11 @@
8 :key="config.id" :label="config.name" :value="config.id"/> 8 :key="config.id" :label="config.name" :value="config.id"/>
9 </el-select> 9 </el-select>
10 </el-form-item> 10 </el-form-item>
11 - <el-form-item label="表名称" prop="tableName">  
12 - <el-input v-model="queryParams.tableName" placeholder="请输入表名称" clearable @keyup.enter.native="handleQuery" /> 11 + <el-form-item label="表名称" prop="name">
  12 + <el-input v-model="queryParams.name" placeholder="请输入表名称" clearable @keyup.enter.native="handleQuery" />
13 </el-form-item> 13 </el-form-item>
14 - <el-form-item label="表描述" prop="tableComment">  
15 - <el-input v-model="queryParams.tableComment" placeholder="请输入表描述" clearable @keyup.enter.native="handleQuery"/> 14 + <el-form-item label="表描述" prop="comment">
  15 + <el-input v-model="queryParams.comment" placeholder="请输入表描述" clearable @keyup.enter.native="handleQuery"/>
16 </el-form-item> 16 </el-form-item>
17 <el-form-item> 17 <el-form-item>
18 <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button> 18 <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
@@ -20,15 +20,11 @@ @@ -20,15 +20,11 @@
20 </el-form-item> 20 </el-form-item>
21 </el-form> 21 </el-form>
22 <el-row> 22 <el-row>
23 - <el-table @row-click="clickRow" ref="table" :data="dbTableList" @selection-change="handleSelectionChange" height="260px"> 23 + <el-table v-loading="loading" @row-click="clickRow" ref="table" :data="dbTableList"
  24 + @selection-change="handleSelectionChange" height="260px">
24 <el-table-column type="selection" width="55" /> 25 <el-table-column type="selection" width="55" />
25 - <el-table-column prop="tableName" label="表名称" :show-overflow-tooltip="true" />  
26 - <el-table-column prop="tableComment" label="表描述" :show-overflow-tooltip="true" />  
27 - <el-table-column prop="createTime" label="创建时间">  
28 - <template slot-scope="scope">  
29 - <span>{{ parseTime(scope.row.createTime) }}</span>  
30 - </template>  
31 - </el-table-column> 26 + <el-table-column prop="name" label="表名称" :show-overflow-tooltip="true" />
  27 + <el-table-column prop="comment" label="表描述" :show-overflow-tooltip="true" />
32 </el-table> 28 </el-table>
33 </el-row> 29 </el-row>
34 <div slot="footer" class="dialog-footer"> 30 <div slot="footer" class="dialog-footer">
@@ -39,12 +35,14 @@ @@ -39,12 +35,14 @@
39 </template> 35 </template>
40 36
41 <script> 37 <script>
42 -import { getSchemaTableList, createCodegenListFromDB } from "@/api/infra/codegen"; 38 +import { getSchemaTableList, createCodegenList } from "@/api/infra/codegen";
43 import {getDataSourceConfigList} from "@/api/infra/dataSourceConfig"; 39 import {getDataSourceConfigList} from "@/api/infra/dataSourceConfig";
44 export default { 40 export default {
45 data() { 41 data() {
46 return { 42 return {
47 // 遮罩层 43 // 遮罩层
  44 + loading: false,
  45 + // 遮罩层
48 visible: false, 46 visible: false,
49 // 选中数组值 47 // 选中数组值
50 tables: [], 48 tables: [],
@@ -55,8 +53,8 @@ export default { @@ -55,8 +53,8 @@ export default {
55 // 查询参数 53 // 查询参数
56 queryParams: { 54 queryParams: {
57 dataSourceConfigId: undefined, 55 dataSourceConfigId: undefined,
58 - tableName: undefined,  
59 - tableComment: undefined, 56 + name: undefined,
  57 + comment: undefined,
60 }, 58 },
61 // 数据源列表 59 // 数据源列表
62 dataSourceConfigs: [], 60 dataSourceConfigs: [],
@@ -79,12 +77,15 @@ export default { @@ -79,12 +77,15 @@ export default {
79 }, 77 },
80 // 多选框选中数据 78 // 多选框选中数据
81 handleSelectionChange(selection) { 79 handleSelectionChange(selection) {
82 - this.tables = selection.map(item => item.tableName); 80 + this.tables = selection.map(item => item.name);
83 }, 81 },
84 // 查询表数据 82 // 查询表数据
85 getList() { 83 getList() {
  84 + this.loading = true;
86 getSchemaTableList(this.queryParams).then(res => { 85 getSchemaTableList(this.queryParams).then(res => {
87 this.dbTableList = res.data; 86 this.dbTableList = res.data;
  87 + }).finally(() => {
  88 + this.loading = false;
88 }); 89 });
89 }, 90 },
90 /** 搜索按钮操作 */ 91 /** 搜索按钮操作 */
@@ -99,7 +100,10 @@ export default { @@ -99,7 +100,10 @@ export default {
99 }, 100 },
100 /** 导入按钮操作 */ 101 /** 导入按钮操作 */
101 handleImportTable() { 102 handleImportTable() {
102 - createCodegenListFromDB(this.tables.join(",")).then(res => { 103 + createCodegenList({
  104 + dataSourceConfigId: this.queryParams.dataSourceConfigId,
  105 + tableNames: this.tables
  106 + }).then(res => {
103 this.$modal.msgSuccess("导入成功"); 107 this.$modal.msgSuccess("导入成功");
104 this.visible = false; 108 this.visible = false;
105 this.$emit("ok"); 109 this.$emit("ok");
yudao-ui-admin/src/views/infra/codegen/index.vue
@@ -26,29 +26,28 @@ @@ -26,29 +26,28 @@
26 <el-row :gutter="10" class="mb8"> 26 <el-row :gutter="10" class="mb8">
27 <el-col :span="1.5"> 27 <el-col :span="1.5">
28 <el-button type="info" plain icon="el-icon-upload" size="mini" @click="openImportTable" 28 <el-button type="info" plain icon="el-icon-upload" size="mini" @click="openImportTable"
29 - v-hasPermi="['infra:codegen:create']">基于 DB 导入</el-button>  
30 - <el-button type="info" plain icon="el-icon-upload" size="mini" @click="openImportSQL"  
31 - v-hasPermi="['infra:codegen:create']">基于 SQL 导入</el-button> 29 + v-hasPermi="['infra:codegen:create']">导入</el-button>
32 </el-col> 30 </el-col>
33 <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar> 31 <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
34 </el-row> 32 </el-row>
35 33
36 <!-- 列表 --> 34 <!-- 列表 -->
37 <el-table v-loading="loading" :data="tableList"> 35 <el-table v-loading="loading" :data="tableList">
38 - <el-table-column label="表名称" align="center" prop="tableName" :show-overflow-tooltip="true" width="200"/> 36 + <el-table-column label="数据源" align="center" :formatter="dataSourceConfigNameFormat"/>
  37 + <el-table-column label="表名称" align="center" prop="tableName" width="200"/>
39 <el-table-column label="表描述" align="center" prop="tableComment" :show-overflow-tooltip="true" width="120"/> 38 <el-table-column label="表描述" align="center" prop="tableComment" :show-overflow-tooltip="true" width="120"/>
40 - <el-table-column label="实体" align="center" prop="className" :show-overflow-tooltip="true" width="200"/>  
41 - <el-table-column label="创建时间" align="center" prop="createTime" width="160"> 39 + <el-table-column label="实体" align="center" prop="className" width="200"/>
  40 + <el-table-column label="创建时间" align="center" prop="createTime" width="180">
42 <template slot-scope="scope"> 41 <template slot-scope="scope">
43 <span>{{ parseTime(scope.row.createTime) }}</span> 42 <span>{{ parseTime(scope.row.createTime) }}</span>
44 </template> 43 </template>
45 </el-table-column> 44 </el-table-column>
46 - <el-table-column label="更新时间" align="center" prop="createTime" width="160"> 45 + <el-table-column label="更新时间" align="center" prop="createTime" width="180">
47 <template slot-scope="scope"> 46 <template slot-scope="scope">
48 <span>{{ parseTime(scope.row.updateTime) }}</span> 47 <span>{{ parseTime(scope.row.updateTime) }}</span>
49 </template> 48 </template>
50 </el-table-column> 49 </el-table-column>
51 - <el-table-column label="操作" align="center" class-name="small-padding fixed-width"> 50 + <el-table-column label="操作" align="center" width="300px" class-name="small-padding fixed-width">
52 <template slot-scope="scope"> 51 <template slot-scope="scope">
53 <el-button type="text" size="small" icon="el-icon-view" @click="handlePreview(scope.row)" v-hasPermi="['infra:codegen:preview']">预览</el-button> 52 <el-button type="text" size="small" icon="el-icon-view" @click="handlePreview(scope.row)" v-hasPermi="['infra:codegen:preview']">预览</el-button>
54 <el-button type="text" size="small" icon="el-icon-edit" @click="handleEditTable(scope.row)" v-hasPermi="['infra:codegen:update']">编辑</el-button> 53 <el-button type="text" size="small" icon="el-icon-edit" @click="handleEditTable(scope.row)" v-hasPermi="['infra:codegen:update']">编辑</el-button>
@@ -81,23 +80,6 @@ @@ -81,23 +80,6 @@
81 80
82 <!-- 基于 DB 导入 --> 81 <!-- 基于 DB 导入 -->
83 <import-table ref="import" @ok="handleQuery" /> 82 <import-table ref="import" @ok="handleQuery" />
84 -  
85 - <!-- 基于 SQL 导入 -->  
86 - <el-dialog :title="importSQL.title" :visible.sync="importSQL.open" width="800px" append-to-body>  
87 - <el-form ref="importSQLForm" :model="importSQL.form" :rules="importSQL.rules" label-width="120px">  
88 - <el-row>  
89 - <el-col :span="12">  
90 - <el-form-item label="建表 SQL 语句" prop="sql">  
91 - <el-input v-model="importSQL.form.sql" type="textarea" rows="30" style="width: 650px;" placeholder="请输入建 SQL 语句" />  
92 - </el-form-item>  
93 - </el-col>  
94 - </el-row>  
95 - </el-form>  
96 - <div slot="footer" class="dialog-footer">  
97 - <el-button type="primary" @click="submitImportSQLForm">确 定</el-button>  
98 - <el-button @click="cancel">取 消</el-button>  
99 - </div>  
100 - </el-dialog>  
101 </div> 83 </div>
102 </template> 84 </template>
103 85
@@ -109,6 +91,7 @@ import importTable from &quot;./importTable&quot;; @@ -109,6 +91,7 @@ import importTable from &quot;./importTable&quot;;
109 // 代码高亮插件 91 // 代码高亮插件
110 import hljs from "highlight.js/lib/highlight"; 92 import hljs from "highlight.js/lib/highlight";
111 import "highlight.js/styles/github-gist.css"; 93 import "highlight.js/styles/github-gist.css";
  94 +import {getDataSourceConfigList} from "@/api/infra/dataSourceConfig";
112 hljs.registerLanguage("java", require("highlight.js/lib/languages/java")); 95 hljs.registerLanguage("java", require("highlight.js/lib/languages/java"));
113 hljs.registerLanguage("xml", require("highlight.js/lib/languages/xml")); 96 hljs.registerLanguage("xml", require("highlight.js/lib/languages/xml"));
114 hljs.registerLanguage("html", require("highlight.js/lib/languages/xml")); 97 hljs.registerLanguage("html", require("highlight.js/lib/languages/xml"));
@@ -150,21 +133,16 @@ export default { @@ -150,21 +133,16 @@ export default {
150 data: {}, 133 data: {},
151 activeName: "", 134 activeName: "",
152 }, 135 },
153 - // 基于 SQL 导入  
154 - importSQL: {  
155 - open: false,  
156 - title: "",  
157 - form: {  
158 -  
159 - },  
160 - rules: {  
161 - sql: [{ required: true, message: "SQL 不能为空", trigger: "blur" }]  
162 - }  
163 - } 136 + // 数据源列表
  137 + dataSourceConfigs: [],
164 }; 138 };
165 }, 139 },
166 created() { 140 created() {
167 this.getList(); 141 this.getList();
  142 + // 加载数据源
  143 + getDataSourceConfigList().then(response => {
  144 + this.dataSourceConfigs = response.data;
  145 + });
168 }, 146 },
169 activated() { 147 activated() {
170 const time = this.$route.query.t; 148 const time = this.$route.query.t;
@@ -200,12 +178,6 @@ export default { @@ -200,12 +178,6 @@ export default {
200 }, 178 },
201 /** 同步数据库操作 */ 179 /** 同步数据库操作 */
202 handleSynchDb(row) { 180 handleSynchDb(row) {
203 - // 基于 SQL 同步  
204 - if (row.importType === 2) {  
205 - this.importSQL.open = true;  
206 - this.importSQL.form.tableId = row.id;  
207 - return;  
208 - }  
209 // 基于 DB 同步 181 // 基于 DB 同步
210 const tableName = row.tableName; 182 const tableName = row.tableName;
211 this.$modal.confirm('确认要强制同步"' + tableName + '"表结构吗?').then(function() { 183 this.$modal.confirm('确认要强制同步"' + tableName + '"表结构吗?').then(function() {
@@ -218,10 +190,6 @@ export default { @@ -218,10 +190,6 @@ export default {
218 openImportTable() { 190 openImportTable() {
219 this.$refs.import.show(); 191 this.$refs.import.show();
220 }, 192 },
221 - /** 打开 SQL 导入的弹窗 **/  
222 - openImportSQL() {  
223 - this.importSQL.open = true;  
224 - },  
225 /** 重置按钮操作 */ 193 /** 重置按钮操作 */
226 resetQuery() { 194 resetQuery() {
227 this.dateRange = []; 195 this.dateRange = [];
@@ -336,43 +304,15 @@ export default { @@ -336,43 +304,15 @@ export default {
336 this.$modal.msgSuccess("删除成功"); 304 this.$modal.msgSuccess("删除成功");
337 }).catch(() => {}); 305 }).catch(() => {});
338 }, 306 },
339 - // 取消按钮  
340 - cancel() {  
341 - this.importSQL.open = false;  
342 - this.reset();  
343 - },  
344 - // 表单重置  
345 - reset() {  
346 - this.importSQL.form = {  
347 - tableId: undefined,  
348 - sql: undefined,  
349 - };  
350 - this.resetForm("importSQLForm");  
351 - },  
352 - // 提交 import SQL 表单  
353 - submitImportSQLForm() {  
354 - this.$refs["importSQLForm"].validate(valid => {  
355 - if (!valid) {  
356 - return;  
357 - }  
358 - // 修改的提交  
359 - let form = this.importSQL.form;  
360 - if (form.tableId != null) {  
361 - syncCodegenFromSQL(form.tableId, form.sql).then(response => {  
362 - this.$modal.msgSuccess("同步成功");  
363 - this.importSQL.open = false;  
364 - this.getList();  
365 - });  
366 - return; 307 + // 数据源配置的名字
  308 + dataSourceConfigNameFormat(row, column) {
  309 + for (const config of this.dataSourceConfigs) {
  310 + if (row.dataSourceConfigId === config.id) {
  311 + return config.name;
367 } 312 }
368 - // 添加的提交  
369 - createCodegenListFromSQL(form).then(response => {  
370 - this.$modal.msgSuccess("导入成功");  
371 - this.importSQL.open = false;  
372 - this.getList();  
373 - });  
374 - });  
375 - } 313 + }
  314 + return '未知【' + row.leaderUserId + '】';
  315 + },
376 } 316 }
377 }; 317 };
378 </script> 318 </script>