datas = ConfigConvert.INSTANCE.convertList(list);
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenColumnDO.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenColumnDO.java
index f1990f3fc..368162214 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenColumnDO.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenColumnDO.java
@@ -39,27 +39,38 @@ public class CodegenColumnDO extends BaseDO {
/**
* 字段名
+ *
+ * 关联 {@link TableField#getName()}
*/
private String columnName;
/**
* 数据库字段类型
+ *
* 关联 {@link TableField.MetaInfo#getJdbcType()}
*/
private String dataType;
/**
* 字段描述
+ *
+ * 关联 {@link TableField#getComment()}
*/
private String columnComment;
/**
* 是否允许为空
+ *
+ * 关联 {@link TableField.MetaInfo#isNullable()}
*/
private Boolean nullable;
/**
* 是否主键
+ *
+ * 关联 {@link TableField#isKeyFlag()}
*/
private Boolean primaryKey;
/**
* 是否自增
+ *
+ * 关联 {@link TableField#isKeyIdentityFlag()}
*/
private Boolean autoIncrement;
/**
@@ -71,12 +82,16 @@ public class CodegenColumnDO extends BaseDO {
/**
* Java 属性类型
- *
+ *
* 例如说 String、Boolean 等等
+ *
+ * 关联 {@link TableField#getColumnType()}
*/
private String javaType;
/**
* Java 属性名
+ *
+ * 关联 {@link TableField#getPropertyName()}
*/
private String javaField;
/**
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenTableDO.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenTableDO.java
index b821d210c..4f4a644a7 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenTableDO.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/dal/dataobject/codegen/CodegenTableDO.java
@@ -6,6 +6,7 @@ import cn.iocoder.yudao.module.infra.enums.codegen.CodegenSceneEnum;
import cn.iocoder.yudao.module.infra.enums.codegen.CodegenTemplateTypeEnum;
import com.baomidou.mybatisplus.annotation.KeySequence;
import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.generator.config.po.TableInfo;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.experimental.Accessors;
@@ -44,10 +45,14 @@ public class CodegenTableDO extends BaseDO {
/**
* 表名称
+ *
+ * 关联 {@link TableInfo#getName()}
*/
private String tableName;
/**
* 表描述
+ *
+ * 关联 {@link TableInfo#getComment()}
*/
private String tableComment;
/**
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenServiceImpl.java
index b5103bc04..c4a9fb801 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/codegen/CodegenServiceImpl.java
@@ -28,6 +28,7 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
+import java.util.function.BiPredicate;
import java.util.stream.Collectors;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
@@ -75,7 +76,7 @@ public class CodegenServiceImpl implements CodegenService {
private Long createCodegen0(Long userId, Long dataSourceConfigId, TableInfo tableInfo) {
// 校验导入的表和字段非空
- checkTableInfo(tableInfo);
+ validateTableInfo(tableInfo);
// 校验是否已经存在
if (codegenTableMapper.selectByTableNameAndDataSourceConfigId(tableInfo.getName(),
dataSourceConfigId) != null) {
@@ -86,7 +87,7 @@ public class CodegenServiceImpl implements CodegenService {
CodegenTableDO table = codegenBuilder.buildTable(tableInfo);
table.setDataSourceConfigId(dataSourceConfigId);
table.setScene(CodegenSceneEnum.ADMIN.getScene()); // 默认配置下,使用管理后台的模板
- table.setAuthor(userApi.getUser(userId).getData().getNickname());
+ table.setAuthor(userApi.getUser(userId).getCheckedData().getNickname());
codegenTableMapper.insert(table);
// 构建 CodegenColumnDO 数组,插入到 DB 中
@@ -99,7 +100,7 @@ public class CodegenServiceImpl implements CodegenService {
return table.getId();
}
- private void checkTableInfo(TableInfo tableInfo) {
+ private void validateTableInfo(TableInfo tableInfo) {
if (tableInfo == null) {
throw exception(CODEGEN_IMPORT_TABLE_NULL);
}
@@ -148,18 +149,33 @@ public class CodegenServiceImpl implements CodegenService {
private void syncCodegen0(Long tableId, TableInfo tableInfo) {
// 校验导入的表和字段非空
- checkTableInfo(tableInfo);
+ validateTableInfo(tableInfo);
List tableFields = tableInfo.getFields();
// 构建 CodegenColumnDO 数组,只同步新增的字段
List codegenColumns = codegenColumnMapper.selectListByTableId(tableId);
Set codegenColumnNames = CollectionUtils.convertSet(codegenColumns, CodegenColumnDO::getColumnName);
+
+ //计算需要修改的字段,插入时重新插入,删除时将原来的删除
+ BiPredicate pr =
+ (tableField, codegenColumn) -> tableField.getType().equals(codegenColumn.getDataType())
+ && tableField.getMetaInfo().isNullable() == codegenColumn.getNullable()
+ && tableField.isKeyFlag() == codegenColumn.getPrimaryKey()
+ && tableField.getComment().equals(codegenColumn.getColumnComment());
+ Map codegenColumnDOMap = CollectionUtils.convertMap(codegenColumns, CodegenColumnDO::getColumnName);
+ //需要修改的字段
+ Set modifyFieldNames = tableFields.stream()
+ .filter(tableField -> codegenColumnDOMap.get(tableField.getColumnName()) != null
+ && !pr.test(tableField, codegenColumnDOMap.get(tableField.getColumnName())))
+ .map(TableField::getColumnName)
+ .collect(Collectors.toSet());
// 计算需要删除的字段
Set tableFieldNames = CollectionUtils.convertSet(tableFields, TableField::getName);
- Set deleteColumnIds = codegenColumns.stream().filter(column -> !tableFieldNames.contains(column.getColumnName()))
+ Set deleteColumnIds = codegenColumns.stream()
+ .filter(column -> (!tableFieldNames.contains(column.getColumnName())) || modifyFieldNames.contains(column.getColumnName()))
.map(CodegenColumnDO::getId).collect(Collectors.toSet());
// 移除已经存在的字段
- tableFields.removeIf(column -> codegenColumnNames.contains(column.getColumnName()));
+ tableFields.removeIf(column -> codegenColumnNames.contains(column.getColumnName()) && (!modifyFieldNames.contains(column.getColumnName())));
if (CollUtil.isEmpty(tableFields) && CollUtil.isEmpty(deleteColumnIds)) {
throw exception(CODEGEN_SYNC_NONE_CHANGE);
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImpl.java
index 5c354c989..51c912be7 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImpl.java
@@ -9,7 +9,6 @@ import cn.iocoder.yudao.module.infra.controller.admin.config.vo.ConfigUpdateReqV
import cn.iocoder.yudao.module.infra.convert.config.ConfigConvert;
import cn.iocoder.yudao.module.infra.dal.dataobject.config.ConfigDO;
import cn.iocoder.yudao.module.infra.dal.mysql.config.ConfigMapper;
-import cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants;
import cn.iocoder.yudao.module.infra.enums.config.ConfigTypeEnum;
import com.google.common.annotations.VisibleForTesting;
import lombok.extern.slf4j.Slf4j;
@@ -20,6 +19,7 @@ import javax.annotation.Resource;
import java.util.List;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.*;
/**
* 参数配置 Service 实现类
@@ -35,7 +35,7 @@ public class ConfigServiceImpl implements ConfigService {
@Override
public Long createConfig(ConfigCreateReqVO reqVO) {
// 校验正确性
- checkCreateOrUpdate(null, reqVO.getKey());
+ validateConfigForCreateOrUpdate(null, reqVO.getKey());
// 插入参数配置
ConfigDO config = ConfigConvert.INSTANCE.convert(reqVO);
config.setType(ConfigTypeEnum.CUSTOM.getType());
@@ -46,19 +46,19 @@ public class ConfigServiceImpl implements ConfigService {
@Override
public void updateConfig(ConfigUpdateReqVO reqVO) {
// 校验正确性
- checkCreateOrUpdate(reqVO.getId(), null); // 不允许更新 key
+ validateConfigForCreateOrUpdate(reqVO.getId(), null); // 不允许更新 key
// 更新参数配置
ConfigDO updateObj = ConfigConvert.INSTANCE.convert(reqVO);
- configMapper.updateById(updateObj);;
+ configMapper.updateById(updateObj);
}
@Override
public void deleteConfig(Long id) {
// 校验配置存在
- ConfigDO config = checkConfigExists(id);
+ ConfigDO config = validateConfigExists(id);
// 内置配置,不允许删除
if (ConfigTypeEnum.SYSTEM.getType().equals(config.getType())) {
- throw exception(ErrorCodeConstants.CONFIG_CAN_NOT_DELETE_SYSTEM_TYPE);
+ throw exception(CONFIG_CAN_NOT_DELETE_SYSTEM_TYPE);
}
// 删除
configMapper.deleteById(id);
@@ -84,39 +84,39 @@ public class ConfigServiceImpl implements ConfigService {
return configMapper.selectList(reqVO);
}
- private void checkCreateOrUpdate(Long id, String key) {
+ private void validateConfigForCreateOrUpdate(Long id, String key) {
// 校验自己存在
- checkConfigExists(id);
+ validateConfigExists(id);
// 校验参数配置 key 的唯一性
if (StrUtil.isNotEmpty(key)) {
- checkConfigKeyUnique(id, key);
+ validateConfigKeyUnique(id, key);
}
}
@VisibleForTesting
- public ConfigDO checkConfigExists(Long id) {
+ public ConfigDO validateConfigExists(Long id) {
if (id == null) {
return null;
}
ConfigDO config = configMapper.selectById(id);
if (config == null) {
- throw exception(ErrorCodeConstants.CONFIG_NOT_EXISTS);
+ throw exception(CONFIG_NOT_EXISTS);
}
return config;
}
@VisibleForTesting
- public void checkConfigKeyUnique(Long id, String key) {
+ public void validateConfigKeyUnique(Long id, String key) {
ConfigDO config = configMapper.selectByKey(key);
if (config == null) {
return;
}
// 如果 id 为空,说明不用比较是否为相同 id 的参数配置
if (id == null) {
- throw exception(ErrorCodeConstants.CONFIG_KEY_DUPLICATE);
+ throw exception(CONFIG_KEY_DUPLICATE);
}
if (!config.getId().equals(id)) {
- throw exception(ErrorCodeConstants.CONFIG_KEY_DUPLICATE);
+ throw exception(CONFIG_KEY_DUPLICATE);
}
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImpl.java
index f2fd0a408..e4365c205 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImpl.java
@@ -37,7 +37,7 @@ public class DataSourceConfigServiceImpl implements DataSourceConfigService {
@Override
public Long createDataSourceConfig(DataSourceConfigCreateReqVO createReqVO) {
DataSourceConfigDO dataSourceConfig = DataSourceConfigConvert.INSTANCE.convert(createReqVO);
- checkConnectionOK(dataSourceConfig);
+ validateConnectionOK(dataSourceConfig);
// 插入
dataSourceConfigMapper.insert(dataSourceConfig);
@@ -50,7 +50,7 @@ public class DataSourceConfigServiceImpl implements DataSourceConfigService {
// 校验存在
validateDataSourceConfigExists(updateReqVO.getId());
DataSourceConfigDO updateObj = DataSourceConfigConvert.INSTANCE.convert(updateReqVO);
- checkConnectionOK(updateObj);
+ validateConnectionOK(updateObj);
// 更新
dataSourceConfigMapper.updateById(updateObj);
@@ -88,7 +88,7 @@ public class DataSourceConfigServiceImpl implements DataSourceConfigService {
return result;
}
- private void checkConnectionOK(DataSourceConfigDO config) {
+ private void validateConnectionOK(DataSourceConfigDO config) {
boolean success = JdbcUtils.isConnectionOK(config.getUrl(), config.getUsername(), config.getPassword());
if (!success) {
throw exception(DATA_SOURCE_CONFIG_NOT_OK);
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImpl.java
index cd3ddaba7..8bd2d5c93 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImpl.java
@@ -41,7 +41,7 @@ public class DatabaseTableServiceImpl implements DatabaseTableService {
return CollUtil.getFirst(getTableList0(dataSourceConfigId, name));
}
- public List getTableList0(Long dataSourceConfigId, String name) {
+ private List getTableList0(Long dataSourceConfigId, String name) {
// 获得数据源配置
DataSourceConfigDO config = dataSourceConfigService.getDataSourceConfig(dataSourceConfigId);
Assert.notNull(config, "数据源({}) 不存在!", dataSourceConfigId);
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigService.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigService.java
index b3fc6bad2..43ab5bc68 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigService.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigService.java
@@ -8,8 +8,6 @@ import cn.iocoder.yudao.module.infra.controller.admin.file.vo.config.FileConfigU
import cn.iocoder.yudao.module.infra.dal.dataobject.file.FileConfigDO;
import javax.validation.Valid;
-import java.util.Collection;
-import java.util.List;
/**
* 文件配置 Service 接口
@@ -60,14 +58,6 @@ public interface FileConfigService {
*/
FileConfigDO getFileConfig(Long id);
- /**
- * 获得文件配置列表
- *
- * @param ids 编号
- * @return 文件配置列表
- */
- List getFileConfigList(Collection ids);
-
/**
* 获得文件配置分页
*
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImpl.java
index e81be2e73..6236df6ff 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImpl.java
@@ -27,7 +27,6 @@ import org.springframework.validation.annotation.Validated;
import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import javax.validation.Validator;
-import java.util.Collection;
import java.util.List;
import java.util.Map;
@@ -95,7 +94,7 @@ public class FileConfigServiceImpl implements FileConfigService {
@Override
public void updateFileConfig(FileConfigUpdateReqVO updateReqVO) {
// 校验存在
- FileConfigDO config = this.validateFileConfigExists(updateReqVO.getId());
+ FileConfigDO config = validateFileConfigExists(updateReqVO.getId());
// 更新
FileConfigDO updateObj = FileConfigConvert.INSTANCE.convert(updateReqVO)
.setConfig(parseClientConfig(config.getStorage(), updateReqVO.getConfig()));
@@ -108,7 +107,7 @@ public class FileConfigServiceImpl implements FileConfigService {
@Transactional(rollbackFor = Exception.class)
public void updateFileConfigMaster(Long id) {
// 校验存在
- this.validateFileConfigExists(id);
+ validateFileConfigExists(id);
// 更新其它为非 master
fileConfigMapper.updateBatch(new FileConfigDO().setMaster(false));
// 更新
@@ -138,9 +137,9 @@ public class FileConfigServiceImpl implements FileConfigService {
@Override
public void deleteFileConfig(Long id) {
// 校验存在
- FileConfigDO config = this.validateFileConfigExists(id);
+ FileConfigDO config = validateFileConfigExists(id);
if (Boolean.TRUE.equals(config.getMaster())) {
- throw exception(FILE_CONFIG_DELETE_FAIL_MASTER);
+ throw exception(FILE_CONFIG_DELETE_FAIL_MASTER);
}
// 删除
fileConfigMapper.deleteById(id);
@@ -161,11 +160,6 @@ public class FileConfigServiceImpl implements FileConfigService {
return fileConfigMapper.selectById(id);
}
- @Override
- public List getFileConfigList(Collection ids) {
- return fileConfigMapper.selectBatchIds(ids);
- }
-
@Override
public PageResult getFileConfigPage(FileConfigPageReqVO pageReqVO) {
return fileConfigMapper.selectPage(pageReqVO);
@@ -174,7 +168,7 @@ public class FileConfigServiceImpl implements FileConfigService {
@Override
public String testFileConfig(Long id) throws Exception {
// 校验存在
- this.validateFileConfigExists(id);
+ validateFileConfigExists(id);
// 上传文件
byte[] content = ResourceUtil.readBytes("file/erweima.jpg");
return fileClientFactory.getFileClient(id).upload(content, IdUtil.fastSimpleUUID() + ".jpg", "image/jpeg");
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImpl.java
index 2226e7bae..0732765d8 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImpl.java
@@ -69,7 +69,7 @@ public class FileServiceImpl implements FileService {
@Override
public void deleteFile(Long id) throws Exception {
// 校验存在
- FileDO file = this.validateFileExists(id);
+ FileDO file = validateFileExists(id);
// 从文件存储器中删除
FileClient client = fileConfigService.getFileClient(file.getConfigId());
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImpl.java
index 6d79f8754..c0f9252af 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImpl.java
@@ -1,17 +1,13 @@
package cn.iocoder.yudao.module.infra.service.logger;
-import cn.iocoder.yudao.framework.apilog.core.service.ApiErrorLog;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.module.infra.api.logger.dto.ApiErrorLogCreateReqDTO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apierrorlog.ApiErrorLogExportReqVO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apierrorlog.ApiErrorLogPageReqVO;
import cn.iocoder.yudao.module.infra.convert.logger.ApiErrorLogConvert;
import cn.iocoder.yudao.module.infra.dal.dataobject.logger.ApiErrorLogDO;
import cn.iocoder.yudao.module.infra.dal.mysql.logger.ApiErrorLogMapper;
-import cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil;
-import cn.iocoder.yudao.framework.common.pojo.PageResult;
-import cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants;
import cn.iocoder.yudao.module.infra.enums.logger.ApiErrorLogProcessStatusEnum;
-import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.validation.annotation.Validated;
@@ -19,6 +15,10 @@ import javax.annotation.Resource;
import java.time.LocalDateTime;
import java.util.List;
+import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
+import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.API_ERROR_LOG_NOT_FOUND;
+import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.API_ERROR_LOG_PROCESSED;
+
/**
* API 错误日志 Service 实现类
*
@@ -33,8 +33,8 @@ public class ApiErrorLogServiceImpl implements ApiErrorLogService {
@Override
public void createApiErrorLog(ApiErrorLogCreateReqDTO createDTO) {
- ApiErrorLogDO apiErrorLog = ApiErrorLogConvert.INSTANCE.convert(createDTO);
- apiErrorLog.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
+ ApiErrorLogDO apiErrorLog = ApiErrorLogConvert.INSTANCE.convert(createDTO)
+ .setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
apiErrorLogMapper.insert(apiErrorLog);
}
@@ -52,10 +52,10 @@ public class ApiErrorLogServiceImpl implements ApiErrorLogService {
public void updateApiErrorLogProcess(Long id, Integer processStatus, Long processUserId) {
ApiErrorLogDO errorLog = apiErrorLogMapper.selectById(id);
if (errorLog == null) {
- throw ServiceExceptionUtil.exception(ErrorCodeConstants.API_ERROR_LOG_NOT_FOUND);
+ throw exception(API_ERROR_LOG_NOT_FOUND);
}
if (!ApiErrorLogProcessStatusEnum.INIT.getStatus().equals(errorLog.getProcessStatus())) {
- throw ServiceExceptionUtil.exception(ErrorCodeConstants.API_ERROR_LOG_PROCESSED);
+ throw exception(API_ERROR_LOG_PROCESSED);
}
// 标记处理
apiErrorLogMapper.updateById(ApiErrorLogDO.builder().id(id).processStatus(processStatus)
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/test/TestDemoServiceImpl.java b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/test/TestDemoServiceImpl.java
index 92153b022..f476b5a72 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/test/TestDemoServiceImpl.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/service/test/TestDemoServiceImpl.java
@@ -45,7 +45,7 @@ public class TestDemoServiceImpl implements TestDemoService {
@CacheEvict(value = "test", key = "#updateReqVO.id")
public void updateTestDemo(TestDemoUpdateReqVO updateReqVO) {
// 校验存在
- this.validateTestDemoExists(updateReqVO.getId());
+ validateTestDemoExists(updateReqVO.getId());
// 更新
TestDemoDO updateObj = TestDemoConvert.INSTANCE.convert(updateReqVO);
testDemoMapper.updateById(updateObj);
@@ -55,7 +55,7 @@ public class TestDemoServiceImpl implements TestDemoService {
@CacheEvict(value = "test", key = "#id")
public void deleteTestDemo(Long id) {
// 校验存在
- this.validateTestDemoExists(id);
+ validateTestDemoExists(id);
// 删除
testDemoMapper.deleteById(id);
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/service/serviceImpl.vm b/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/service/serviceImpl.vm
index 85dfa0aab..a732039ce 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/service/serviceImpl.vm
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/service/serviceImpl.vm
@@ -39,7 +39,7 @@ public class ${table.className}ServiceImpl implements ${table.className}Service
@Override
public void update${simpleClassName}(${sceneEnum.prefixClass}${table.className}UpdateReqVO updateReqVO) {
// 校验存在
- this.validate${simpleClassName}Exists(updateReqVO.getId());
+ validate${simpleClassName}Exists(updateReqVO.getId());
// 更新
${table.className}DO updateObj = ${table.className}Convert.INSTANCE.convert(updateReqVO);
${classNameVar}Mapper.updateById(updateObj);
@@ -48,7 +48,7 @@ public class ${table.className}ServiceImpl implements ${table.className}Service
@Override
public void delete${simpleClassName}(${primaryColumn.javaType} id) {
// 校验存在
- this.validate${simpleClassName}Exists(id);
+ validate${simpleClassName}Exists(id);
// 删除
${classNameVar}Mapper.deleteById(id);
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/test/serviceTest.vm b/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/test/serviceTest.vm
index e97fbb275..67a44e989 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/test/serviceTest.vm
+++ b/yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/java/test/serviceTest.vm
@@ -52,7 +52,7 @@ import static org.mockito.Mockito.*;
#if (${column.listOperation})
#set ($JavaField = $column.javaField.substring(0,1).toUpperCase() + ${column.javaField.substring(1)})##首字母大写
#if (${column.listOperationCondition} == "BETWEEN")## BETWEEN 的情况
- reqVO.set${JavaField}((new LocalDateTime[]{}));
+ reqVO.set${JavaField}(buildBetweenTime(2023, 2, 1, 2023, 2, 28));
#else
reqVO.set$JavaField(null);
#end
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImplTest.java
similarity index 73%
rename from yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceTest.java
rename to yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImplTest.java
index 5d7d74338..428b20522 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/config/ConfigServiceImplTest.java
@@ -2,7 +2,6 @@ package cn.iocoder.yudao.module.infra.service.config;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.collection.ArrayUtils;
-import cn.iocoder.yudao.framework.common.util.object.ObjectUtils;
import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
import cn.iocoder.yudao.framework.test.core.util.RandomUtils;
import cn.iocoder.yudao.module.infra.controller.admin.config.vo.ConfigCreateReqVO;
@@ -12,27 +11,25 @@ import cn.iocoder.yudao.module.infra.controller.admin.config.vo.ConfigUpdateReqV
import cn.iocoder.yudao.module.infra.dal.dataobject.config.ConfigDO;
import cn.iocoder.yudao.module.infra.dal.mysql.config.ConfigMapper;
import cn.iocoder.yudao.module.infra.enums.config.ConfigTypeEnum;
-import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.springframework.context.annotation.Import;
import javax.annotation.Resource;
-import java.time.LocalDateTime;
import java.util.List;
import java.util.function.Consumer;
import static cn.hutool.core.util.RandomUtil.randomEle;
-import static cn.iocoder.yudao.framework.common.util.date.DateUtils.buildLocalDateTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildBetweenTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildTime;
+import static cn.iocoder.yudao.framework.common.util.object.ObjectUtils.cloneIgnoreId;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.*;
import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.*;
import static org.junit.jupiter.api.Assertions.*;
-import static org.mockito.Mockito.times;
-import static org.mockito.Mockito.verify;
@Import(ConfigServiceImpl.class)
-public class ConfigServiceTest extends BaseDbUnitTest {
+public class ConfigServiceImplTest extends BaseDbUnitTest {
@Resource
private ConfigServiceImpl configService;
@@ -52,7 +49,7 @@ public class ConfigServiceTest extends BaseDbUnitTest {
// 校验记录的属性是否正确
ConfigDO config = configMapper.selectById(configId);
assertPojoEquals(reqVO, config);
- Assertions.assertEquals(ConfigTypeEnum.CUSTOM.getType(), config.getType());
+ assertEquals(ConfigTypeEnum.CUSTOM.getType(), config.getType());
}
@Test
@@ -103,40 +100,40 @@ public class ConfigServiceTest extends BaseDbUnitTest {
}
@Test
- public void testCheckConfigExists_success() {
+ public void testValidateConfigExists_success() {
// mock 数据
ConfigDO dbConfigDO = randomConfigDO();
configMapper.insert(dbConfigDO);// @Sql: 先插入出一条存在的数据
// 调用成功
- configService.checkConfigExists(dbConfigDO.getId());
+ configService.validateConfigExists(dbConfigDO.getId());
}
@Test
- public void testCheckConfigExist_notExists() {
- assertServiceException(() -> configService.checkConfigExists(randomLongId()), CONFIG_NOT_EXISTS);
+ public void testValidateConfigExist_notExists() {
+ assertServiceException(() -> configService.validateConfigExists(randomLongId()), CONFIG_NOT_EXISTS);
}
@Test
- public void testCheckConfigKeyUnique_success() {
+ public void testValidateConfigKeyUnique_success() {
// 调用,成功
- configService.checkConfigKeyUnique(randomLongId(), randomString());
+ configService.validateConfigKeyUnique(randomLongId(), randomString());
}
@Test
- public void testCheckConfigKeyUnique_keyDuplicateForCreate() {
+ public void testValidateConfigKeyUnique_keyDuplicateForCreate() {
// 准备参数
String key = randomString();
// mock 数据
configMapper.insert(randomConfigDO(o -> o.setConfigKey(key)));
// 调用,校验异常
- assertServiceException(() -> configService.checkConfigKeyUnique(null, key),
+ assertServiceException(() -> configService.validateConfigKeyUnique(null, key),
CONFIG_KEY_DUPLICATE);
}
@Test
- public void testCheckConfigKeyUnique_keyDuplicateForUpdate() {
+ public void testValidateConfigKeyUnique_keyDuplicateForUpdate() {
// 准备参数
Long id = randomLongId();
String key = randomString();
@@ -144,7 +141,7 @@ public class ConfigServiceTest extends BaseDbUnitTest {
configMapper.insert(randomConfigDO(o -> o.setConfigKey(key)));
// 调用,校验异常
- assertServiceException(() -> configService.checkConfigKeyUnique(id, key),
+ assertServiceException(() -> configService.validateConfigKeyUnique(id, key),
CONFIG_KEY_DUPLICATE);
}
@@ -155,23 +152,23 @@ public class ConfigServiceTest extends BaseDbUnitTest {
o.setName("芋艿");
o.setConfigKey("yunai");
o.setType(ConfigTypeEnum.SYSTEM.getType());
- o.setCreateTime(buildLocalDateTime(2021, 2, 1));
+ o.setCreateTime(buildTime(2021, 2, 1));
});
configMapper.insert(dbConfig);
// 测试 name 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setName("土豆")));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setName("土豆")));
// 测试 key 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setConfigKey("tudou")));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setConfigKey("tudou")));
// 测试 type 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setType(ConfigTypeEnum.CUSTOM.getType())));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setType(ConfigTypeEnum.CUSTOM.getType())));
// 测试 createTime 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setCreateTime(buildLocalDateTime(2021, 1, 1))));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setCreateTime(buildTime(2021, 1, 1))));
// 准备参数
ConfigPageReqVO reqVO = new ConfigPageReqVO();
reqVO.setName("艿");
reqVO.setKey("nai");
reqVO.setType(ConfigTypeEnum.SYSTEM.getType());
- reqVO.setCreateTime((new LocalDateTime[]{buildLocalDateTime(2021, 1, 15),buildLocalDateTime(2021, 2, 15)}));
+ reqVO.setCreateTime(buildBetweenTime(2021, 1, 15, 2021, 2, 15));
// 调用
PageResult pageResult = configService.getConfigPage(reqVO);
@@ -188,23 +185,23 @@ public class ConfigServiceTest extends BaseDbUnitTest {
o.setName("芋艿");
o.setConfigKey("yunai");
o.setType(ConfigTypeEnum.SYSTEM.getType());
- o.setCreateTime(buildLocalDateTime(2021, 2, 1));
+ o.setCreateTime(buildTime(2021, 2, 1));
});
configMapper.insert(dbConfig);
// 测试 name 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setName("土豆")));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setName("土豆")));
// 测试 key 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setConfigKey("tudou")));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setConfigKey("tudou")));
// 测试 type 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setType(ConfigTypeEnum.CUSTOM.getType())));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setType(ConfigTypeEnum.CUSTOM.getType())));
// 测试 createTime 不匹配
- configMapper.insert(ObjectUtils.cloneIgnoreId(dbConfig, o -> o.setCreateTime(buildLocalDateTime(2021, 1, 1))));
+ configMapper.insert(cloneIgnoreId(dbConfig, o -> o.setCreateTime(buildTime(2021, 1, 1))));
// 准备参数
ConfigExportReqVO reqVO = new ConfigExportReqVO();
reqVO.setName("艿");
reqVO.setKey("nai");
reqVO.setType(ConfigTypeEnum.SYSTEM.getType());
- reqVO.setCreateTime((new LocalDateTime[]{buildLocalDateTime(2021, 1, 15),buildLocalDateTime(2021, 2, 15)}));
+ reqVO.setCreateTime(buildBetweenTime(2021, 1, 15, 2021, 2, 15));
// 调用
List list = configService.getConfigList(reqVO);
@@ -213,6 +210,21 @@ public class ConfigServiceTest extends BaseDbUnitTest {
assertPojoEquals(dbConfig, list.get(0));
}
+ @Test
+ public void testGetConfig() {
+ // mock 数据
+ ConfigDO dbConfig = randomConfigDO();
+ configMapper.insert(dbConfig);// @Sql: 先插入出一条存在的数据
+ // 准备参数
+ Long id = dbConfig.getId();
+
+ // 调用
+ ConfigDO config = configService.getConfig(id);
+ // 断言
+ assertNotNull(config);
+ assertPojoEquals(dbConfig, config);
+ }
+
@Test
public void testGetConfigByKey() {
// mock 数据
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImplTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImplTest.java
index e1c997f7b..b5ef46c46 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImplTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DataSourceConfigServiceImplTest.java
@@ -1,5 +1,6 @@
package cn.iocoder.yudao.module.infra.service.db;
+import cn.hutool.core.map.MapUtil;
import cn.hutool.core.util.ReflectUtil;
import cn.hutool.crypto.symmetric.AES;
import cn.iocoder.yudao.framework.mybatis.core.type.EncryptTypeHandler;
@@ -9,6 +10,7 @@ import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigCrea
import cn.iocoder.yudao.module.infra.controller.admin.db.vo.DataSourceConfigUpdateReqVO;
import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO;
import cn.iocoder.yudao.module.infra.dal.mysql.db.DataSourceConfigMapper;
+import com.baomidou.dynamic.datasource.spring.boot.autoconfigure.DataSourceProperty;
import com.baomidou.dynamic.datasource.spring.boot.autoconfigure.DynamicDataSourceProperties;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
@@ -18,14 +20,14 @@ import org.springframework.boot.test.mock.mockito.MockBean;
import org.springframework.context.annotation.Import;
import javax.annotation.Resource;
+import java.util.List;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomLongId;
import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomPojo;
import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.DATA_SOURCE_CONFIG_NOT_EXISTS;
-import static org.junit.jupiter.api.Assertions.assertNotNull;
-import static org.junit.jupiter.api.Assertions.assertNull;
+import static org.junit.jupiter.api.Assertions.*;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.mockStatic;
@@ -57,6 +59,11 @@ public class DataSourceConfigServiceImplTest extends BaseDbUnitTest {
ReflectUtil.setFieldValue(EncryptTypeHandler.class, "aes", aes);
when(aes.encryptBase64(anyString())).then((Answer) invocation -> invocation.getArgument(0));
when(aes.decryptStr(anyString())).then((Answer) invocation -> invocation.getArgument(0));
+
+ // mock DynamicDataSourceProperties
+ when(dynamicDataSourceProperties.getPrimary()).thenReturn("primary");
+ when(dynamicDataSourceProperties.getDatasource()).thenReturn(MapUtil.of("primary",
+ new DataSourceProperty().setUrl("http://localhost:3306").setUsername("yunai").setPassword("tudou")));
}
@Test
@@ -89,7 +96,6 @@ public class DataSourceConfigServiceImplTest extends BaseDbUnitTest {
o.setId(dbDataSourceConfig.getId()); // 设置更新的 ID
});
// mock 方法
-// when(stringEncryptor.encrypt(eq(reqVO.getPassword()))).thenReturn("123456");
databaseUtilsMock.when(() -> JdbcUtils.isConnectionOK(eq(reqVO.getUrl()),
eq(reqVO.getUsername()), eq(reqVO.getPassword()))).thenReturn(true);
@@ -142,7 +148,58 @@ public class DataSourceConfigServiceImplTest extends BaseDbUnitTest {
// 调用
DataSourceConfigDO result = dataSourceConfigMapper.selectOne(DataSourceConfigDO::getPassword,
EncryptTypeHandler.encrypt(dbDataSourceConfig.getPassword()));
- System.out.println(result);
+ assertPojoEquals(dbDataSourceConfig, result);
+ }
+
+ @Test
+ public void testGetDataSourceConfig_master() {
+ // 准备参数
+ Long id = 0L;
+ // mock 方法
+
+ // 调用
+ DataSourceConfigDO dataSourceConfig = dataSourceConfigService.getDataSourceConfig(id);
+ // 断言
+ assertEquals(id, dataSourceConfig.getId());
+ assertEquals("primary", dataSourceConfig.getName());
+ assertEquals("http://localhost:3306", dataSourceConfig.getUrl());
+ assertEquals("yunai", dataSourceConfig.getUsername());
+ assertEquals("tudou", dataSourceConfig.getPassword());
+ }
+
+ @Test
+ public void testGetDataSourceConfig_normal() {
+ // mock 数据
+ DataSourceConfigDO dbDataSourceConfig = randomPojo(DataSourceConfigDO.class);
+ dataSourceConfigMapper.insert(dbDataSourceConfig);// @Sql: 先插入出一条存在的数据
+ // 准备参数
+ Long id = dbDataSourceConfig.getId();
+
+ // 调用
+ DataSourceConfigDO dataSourceConfig = dataSourceConfigService.getDataSourceConfig(id);
+ // 断言
+ assertPojoEquals(dbDataSourceConfig, dataSourceConfig);
+ }
+
+ @Test
+ public void testGetDataSourceConfigList() {
+ // mock 数据
+ DataSourceConfigDO dbDataSourceConfig = randomPojo(DataSourceConfigDO.class);
+ dataSourceConfigMapper.insert(dbDataSourceConfig);// @Sql: 先插入出一条存在的数据
+ // 准备参数
+
+ // 调用
+ List dataSourceConfigList = dataSourceConfigService.getDataSourceConfigList();
+ // 断言
+ assertEquals(2, dataSourceConfigList.size());
+ // master
+ assertEquals(0L, dataSourceConfigList.get(0).getId());
+ assertEquals("primary", dataSourceConfigList.get(0).getName());
+ assertEquals("http://localhost:3306", dataSourceConfigList.get(0).getUrl());
+ assertEquals("yunai", dataSourceConfigList.get(0).getUsername());
+ assertEquals("tudou", dataSourceConfigList.get(0).getPassword());
+ // normal
+ assertPojoEquals(dbDataSourceConfig, dataSourceConfigList.get(1));
}
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImplTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImplTest.java
new file mode 100644
index 000000000..6ce8c7d41
--- /dev/null
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/db/DatabaseTableServiceImplTest.java
@@ -0,0 +1,89 @@
+package cn.iocoder.yudao.module.infra.service.db;
+
+import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
+import cn.iocoder.yudao.module.infra.dal.dataobject.db.DataSourceConfigDO;
+import com.baomidou.mybatisplus.generator.config.po.TableField;
+import com.baomidou.mybatisplus.generator.config.po.TableInfo;
+import com.baomidou.mybatisplus.generator.config.rules.DbColumnType;
+import org.apache.ibatis.type.JdbcType;
+import org.junit.jupiter.api.Test;
+import org.springframework.boot.test.mock.mockito.MockBean;
+import org.springframework.context.annotation.Import;
+
+import javax.annotation.Resource;
+import java.util.List;
+
+import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomLongId;
+import static org.junit.jupiter.api.Assertions.*;
+import static org.mockito.ArgumentMatchers.eq;
+import static org.mockito.Mockito.when;
+
+@Import(DatabaseTableServiceImpl.class)
+public class DatabaseTableServiceImplTest extends BaseDbUnitTest {
+
+ @Resource
+ private DatabaseTableServiceImpl databaseTableService;
+
+ @MockBean
+ private DataSourceConfigService dataSourceConfigService;
+
+ @Test
+ public void testGetTableList() {
+ // 准备参数
+ Long dataSourceConfigId = randomLongId();
+ // mock 方法
+ DataSourceConfigDO dataSourceConfig = new DataSourceConfigDO().setUsername("sa").setPassword("")
+ .setUrl("jdbc:h2:mem:testdb");
+ when(dataSourceConfigService.getDataSourceConfig(eq(dataSourceConfigId)))
+ .thenReturn(dataSourceConfig);
+
+ // 调用
+ List tables = databaseTableService.getTableList(dataSourceConfigId,
+ "config", "参数");
+ // 断言
+ assertEquals(1, tables.size());
+ assertTableInfo(tables.get(0));
+ }
+
+ @Test
+ public void testGetTable() {
+ // 准备参数
+ Long dataSourceConfigId = randomLongId();
+ // mock 方法
+ DataSourceConfigDO dataSourceConfig = new DataSourceConfigDO().setUsername("sa").setPassword("")
+ .setUrl("jdbc:h2:mem:testdb");
+ when(dataSourceConfigService.getDataSourceConfig(eq(dataSourceConfigId)))
+ .thenReturn(dataSourceConfig);
+
+ // 调用
+ TableInfo tableInfo = databaseTableService.getTable(dataSourceConfigId, "infra_config");
+ // 断言
+ assertTableInfo(tableInfo);
+ }
+
+ private void assertTableInfo(TableInfo tableInfo) {
+ assertEquals("infra_config", tableInfo.getName());
+ assertEquals("参数配置表", tableInfo.getComment());
+ assertEquals(13, tableInfo.getFields().size());
+ // id 字段
+ TableField idField = tableInfo.getFields().get(0);
+ assertEquals("id", idField.getName());
+ assertEquals(JdbcType.BIGINT, idField.getMetaInfo().getJdbcType());
+ assertEquals("编号", idField.getComment());
+ assertFalse(idField.getMetaInfo().isNullable());
+ assertTrue(idField.isKeyFlag());
+ assertTrue(idField.isKeyIdentityFlag());
+ assertEquals(DbColumnType.LONG, idField.getColumnType());
+ assertEquals("id", idField.getPropertyName());
+ // name 字段
+ TableField nameField = tableInfo.getFields().get(3);
+ assertEquals("name", nameField.getName());
+ assertEquals(JdbcType.VARCHAR, nameField.getMetaInfo().getJdbcType());
+ assertEquals("名字", nameField.getComment());
+ assertFalse(nameField.getMetaInfo().isNullable());
+ assertFalse(nameField.isKeyFlag());
+ assertFalse(nameField.isKeyIdentityFlag());
+ assertEquals(DbColumnType.STRING, nameField.getColumnType());
+ assertEquals("name", nameField.getPropertyName());
+ }
+}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImplTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImplTest.java
index 56261576b..656955194 100755
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImplTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileConfigServiceImplTest.java
@@ -7,6 +7,7 @@ import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.file.core.client.FileClient;
import cn.iocoder.yudao.framework.file.core.client.FileClientConfig;
import cn.iocoder.yudao.framework.file.core.client.FileClientFactory;
+import cn.iocoder.yudao.framework.file.core.client.local.LocalFileClient;
import cn.iocoder.yudao.framework.file.core.client.local.LocalFileClientConfig;
import cn.iocoder.yudao.framework.file.core.enums.FileStorageEnum;
import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
@@ -41,10 +42,10 @@ import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.*;
/**
- * {@link FileConfigServiceImpl} 的单元测试类
- *
- * @author 芋道源码
- */
+* {@link FileConfigServiceImpl} 的单元测试类
+*
+* @author 芋道源码
+*/
@Import(FileConfigServiceImpl.class)
public class FileConfigServiceImplTest extends BaseDbUnitTest {
@@ -171,8 +172,8 @@ public class FileConfigServiceImplTest extends BaseDbUnitTest {
// 调用
fileConfigService.deleteFileConfig(id);
- // 校验数据不存在了
- assertNull(fileConfigMapper.selectById(id));
+ // 校验数据不存在了
+ assertNull(fileConfigMapper.selectById(id));
// verify 调用
verify(fileConfigProducer).sendFileConfigRefreshMessage();
}
@@ -200,30 +201,30 @@ public class FileConfigServiceImplTest extends BaseDbUnitTest {
@Test
public void testGetFileConfigPage() {
- // mock 数据
- FileConfigDO dbFileConfig = randomFileConfigDO().setName("芋道源码")
- .setStorage(FileStorageEnum.LOCAL.getStorage());
- dbFileConfig.setCreateTime(LocalDateTimeUtil.parse("2020-01-23", DatePattern.NORM_DATE_PATTERN));// 等会查询到
- fileConfigMapper.insert(dbFileConfig);
- // 测试 name 不匹配
- fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setName("源码")));
- // 测试 storage 不匹配
- fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setStorage(FileStorageEnum.DB.getStorage())));
- // 测试 createTime 不匹配
- fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setCreateTime(LocalDateTimeUtil.parse("2020-11-23", DatePattern.NORM_DATE_PATTERN))));
- // 准备参数
- FileConfigPageReqVO reqVO = new FileConfigPageReqVO();
- reqVO.setName("芋道");
- reqVO.setStorage(FileStorageEnum.LOCAL.getStorage());
- reqVO.setCreateTime((new LocalDateTime[]{buildTime(2020, 1, 1),
- buildTime(2020, 1, 24)}));
+ // mock 数据
+ FileConfigDO dbFileConfig = randomFileConfigDO().setName("芋道源码")
+ .setStorage(FileStorageEnum.LOCAL.getStorage());
+ dbFileConfig.setCreateTime(LocalDateTimeUtil.parse("2020-01-23", DatePattern.NORM_DATE_PATTERN));// 等会查询到
+ fileConfigMapper.insert(dbFileConfig);
+ // 测试 name 不匹配
+ fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setName("源码")));
+ // 测试 storage 不匹配
+ fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setStorage(FileStorageEnum.DB.getStorage())));
+ // 测试 createTime 不匹配
+ fileConfigMapper.insert(cloneIgnoreId(dbFileConfig, o -> o.setCreateTime(LocalDateTimeUtil.parse("2020-11-23", DatePattern.NORM_DATE_PATTERN))));
+ // 准备参数
+ FileConfigPageReqVO reqVO = new FileConfigPageReqVO();
+ reqVO.setName("芋道");
+ reqVO.setStorage(FileStorageEnum.LOCAL.getStorage());
+ reqVO.setCreateTime((new LocalDateTime[]{buildTime(2020, 1, 1),
+ buildTime(2020, 1, 24)}));
- // 调用
- PageResult pageResult = fileConfigService.getFileConfigPage(reqVO);
- // 断言
- assertEquals(1, pageResult.getTotal());
- assertEquals(1, pageResult.getList().size());
- assertPojoEquals(dbFileConfig, pageResult.getList().get(0));
+ // 调用
+ PageResult pageResult = fileConfigService.getFileConfigPage(reqVO);
+ // 断言
+ assertEquals(1, pageResult.getTotal());
+ assertEquals(1, pageResult.getList().size());
+ assertPojoEquals(dbFileConfig, pageResult.getList().get(0));
}
@Test
@@ -242,6 +243,30 @@ public class FileConfigServiceImplTest extends BaseDbUnitTest {
assertEquals("https://www.iocoder.cn", fileConfigService.testFileConfig(id));
}
+ @Test
+ public void testGetFileConfig() {
+ // mock 数据
+ FileConfigDO dbFileConfig = randomFileConfigDO().setMaster(false);
+ fileConfigMapper.insert(dbFileConfig);// @Sql: 先插入出一条存在的数据
+ // 准备参数
+ Long id = dbFileConfig.getId();
+
+ // 调用,并断言
+ assertPojoEquals(dbFileConfig, fileConfigService.getFileConfig(id));
+ }
+
+ @Test
+ public void testGetFileClient() {
+ // 准备参数
+ Long id = randomLongId();
+ // mock 获得 Client
+ FileClient fileClient = new LocalFileClient(id, new LocalFileClientConfig());
+ when(fileClientFactory.getFileClient(eq(id))).thenReturn(fileClient);
+
+ // 调用,并断言
+ assertSame(fileClient, fileConfigService.getFileClient(id));
+ }
+
private FileConfigDO randomFileConfigDO() {
return randomPojo(FileConfigDO.class).setStorage(randomEle(FileStorageEnum.values()).getStorage())
.setConfig(new EmptyFileClientConfig());
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImplTest.java
similarity index 92%
rename from yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceTest.java
rename to yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImplTest.java
index 1261d0a99..fe5f6fb1e 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/file/FileServiceImplTest.java
@@ -16,7 +16,7 @@ import org.springframework.context.annotation.Import;
import javax.annotation.Resource;
import java.time.LocalDateTime;
-import static cn.iocoder.yudao.framework.common.util.date.DateUtils.buildLocalDateTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildTime;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.*;
import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.FILE_NOT_EXISTS;
@@ -25,7 +25,7 @@ import static org.mockito.ArgumentMatchers.same;
import static org.mockito.Mockito.*;
@Import({FileServiceImpl.class})
-public class FileServiceTest extends BaseDbUnitTest {
+public class FileServiceImplTest extends BaseDbUnitTest {
@Resource
private FileService fileService;
@@ -42,7 +42,7 @@ public class FileServiceTest extends BaseDbUnitTest {
FileDO dbFile = randomPojo(FileDO.class, o -> { // 等会查询到
o.setPath("yunai");
o.setType("image/jpg");
- o.setCreateTime(buildLocalDateTime(2021, 1, 15));
+ o.setCreateTime(buildTime(2021, 1, 15));
});
fileMapper.insert(dbFile);
// 测试 path 不匹配
@@ -53,13 +53,13 @@ public class FileServiceTest extends BaseDbUnitTest {
}));
// 测试 createTime 不匹配
fileMapper.insert(ObjectUtils.cloneIgnoreId(dbFile, o -> {
- o.setCreateTime(buildLocalDateTime(2020, 1, 15));
+ o.setCreateTime(buildTime(2020, 1, 15));
}));
// 准备参数
FilePageReqVO reqVO = new FilePageReqVO();
reqVO.setPath("yunai");
reqVO.setType("jp");
- reqVO.setCreateTime((new LocalDateTime[]{buildLocalDateTime(2021, 1, 10), buildLocalDateTime(2021, 1, 20)}));
+ reqVO.setCreateTime((new LocalDateTime[]{buildTime(2021, 1, 10), buildTime(2021, 1, 20)}));
// 调用
PageResult pageResult = fileService.getFilePage(reqVO);
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiAccessLogServiceImplTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiAccessLogServiceImplTest.java
index cb1e52b23..8ff2dd9bf 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiAccessLogServiceImplTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiAccessLogServiceImplTest.java
@@ -1,12 +1,9 @@
package cn.iocoder.yudao.module.infra.service.logger;
-import cn.hutool.core.util.RandomUtil;
import cn.iocoder.yudao.framework.common.enums.UserTypeEnum;
import cn.iocoder.yudao.framework.common.exception.enums.GlobalErrorCodeConstants;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
-import cn.iocoder.yudao.framework.common.util.object.ObjectUtils;
import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
-import cn.iocoder.yudao.framework.test.core.util.RandomUtils;
import cn.iocoder.yudao.module.infra.api.logger.dto.ApiAccessLogCreateReqDTO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apiaccesslog.ApiAccessLogExportReqVO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apiaccesslog.ApiAccessLogPageReqVO;
@@ -16,149 +13,121 @@ import org.junit.jupiter.api.Test;
import org.springframework.context.annotation.Import;
import javax.annotation.Resource;
-import java.time.LocalDateTime;
import java.util.List;
-import static cn.iocoder.yudao.framework.common.util.date.DateUtils.buildLocalDateTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildBetweenTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildTime;
+import static cn.iocoder.yudao.framework.common.util.object.ObjectUtils.cloneIgnoreId;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
+import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomPojo;
import static org.junit.jupiter.api.Assertions.assertEquals;
-import static org.junit.jupiter.api.Assertions.assertNotNull;
@Import(ApiAccessLogServiceImpl.class)
public class ApiAccessLogServiceImplTest extends BaseDbUnitTest {
@Resource
- private ApiAccessLogService apiAccessLogService;
+ private ApiAccessLogServiceImpl apiAccessLogService;
@Resource
private ApiAccessLogMapper apiAccessLogMapper;
@Test
public void testGetApiAccessLogPage() {
- // 构造测试数据
- long userId = 2233L;
- int userType = UserTypeEnum.ADMIN.getValue();
- String applicationName = "yudao-test";
- String requestUrl = "foo";
- LocalDateTime beginTime = buildLocalDateTime(2021, 3, 13);
- int duration = 1000;
- int resultCode = GlobalErrorCodeConstants.SUCCESS.getCode();
-
- ApiAccessLogDO infApiAccessLogDO = RandomUtils.randomPojo(ApiAccessLogDO.class, dto -> {
- dto.setUserId(userId);
- dto.setUserType(userType);
- dto.setApplicationName(applicationName);
- dto.setRequestUrl(requestUrl);
- dto.setBeginTime(beginTime);
- dto.setDuration(duration);
- dto.setResultCode(resultCode);
+ ApiAccessLogDO apiAccessLogDO = randomPojo(ApiAccessLogDO.class, o -> {
+ o.setUserId(2233L);
+ o.setUserType(UserTypeEnum.ADMIN.getValue());
+ o.setApplicationName("yudao-test");
+ o.setRequestUrl("foo");
+ o.setBeginTime(buildTime(2021, 3, 13));
+ o.setDuration(1000);
+ o.setResultCode(GlobalErrorCodeConstants.SUCCESS.getCode());
});
- apiAccessLogMapper.insert(infApiAccessLogDO);
-
- // 下面几个都是不匹配的数据
- // userId 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setUserId(3344L)));
- // userType
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
- // applicationName 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setApplicationName("test")));
- // requestUrl 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setRequestUrl("bar")));
- // 构造一个早期时间 2021-02-06 00:00:00
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setBeginTime(buildLocalDateTime(2021, 2, 6))));
- // duration 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setDuration(100)));
- // resultCode 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setResultCode(2)));
-
- // 构造调用参数
+ apiAccessLogMapper.insert(apiAccessLogDO);
+ // 测试 userId 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setUserId(3344L)));
+ // 测试 userType 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setUserType(UserTypeEnum.MEMBER.getValue())));
+ // 测试 applicationName 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setApplicationName("test")));
+ // 测试 requestUrl 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setRequestUrl("bar")));
+ // 测试 beginTime 不匹配:构造一个早期时间 2021-02-06 00:00:00
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setBeginTime(buildTime(2021, 2, 6))));
+ // 测试 duration 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setDuration(100)));
+ // 测试 resultCode 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setResultCode(2)));
+ // 准备参数
ApiAccessLogPageReqVO reqVO = new ApiAccessLogPageReqVO();
- reqVO.setUserId(userId);
- reqVO.setUserType(userType);
- reqVO.setApplicationName(applicationName);
- reqVO.setRequestUrl(requestUrl);
- reqVO.setBeginTime((new LocalDateTime[]{buildLocalDateTime(2021, 3, 12),buildLocalDateTime(2021, 3, 14)}));
- reqVO.setDuration(duration);
- reqVO.setResultCode(resultCode);
+ reqVO.setUserId(2233L);
+ reqVO.setUserType(UserTypeEnum.ADMIN.getValue());
+ reqVO.setApplicationName("yudao-test");
+ reqVO.setRequestUrl("foo");
+ reqVO.setBeginTime(buildBetweenTime(2021, 3, 13, 2021, 3, 13));
+ reqVO.setDuration(1000);
+ reqVO.setResultCode(GlobalErrorCodeConstants.SUCCESS.getCode());
- // 调用service方法
+ // 调用
PageResult pageResult = apiAccessLogService.getApiAccessLogPage(reqVO);
-
// 断言,只查到了一条符合条件的
assertEquals(1, pageResult.getTotal());
assertEquals(1, pageResult.getList().size());
- assertPojoEquals(infApiAccessLogDO, pageResult.getList().get(0));
+ assertPojoEquals(apiAccessLogDO, pageResult.getList().get(0));
}
@Test
public void testGetApiAccessLogList() {
- // 构造测试数据
- long userId = 2233L;
- int userType = UserTypeEnum.ADMIN.getValue();
- String applicationName = "yudao-test";
- String requestUrl = "foo";
- LocalDateTime beginTime = buildLocalDateTime(2021, 3, 13);
- int duration = 1000;
- int resultCode = GlobalErrorCodeConstants.SUCCESS.getCode();
-
- ApiAccessLogDO infApiAccessLogDO = RandomUtils.randomPojo(ApiAccessLogDO.class, dto -> {
- dto.setUserId(userId);
- dto.setUserType(userType);
- dto.setApplicationName(applicationName);
- dto.setRequestUrl(requestUrl);
- dto.setBeginTime(beginTime);
- dto.setDuration(duration);
- dto.setResultCode(resultCode);
+ ApiAccessLogDO apiAccessLogDO = randomPojo(ApiAccessLogDO.class, o -> {
+ o.setUserId(2233L);
+ o.setUserType(UserTypeEnum.ADMIN.getValue());
+ o.setApplicationName("yudao-test");
+ o.setRequestUrl("foo");
+ o.setBeginTime(buildTime(2021, 3, 13));
+ o.setDuration(1000);
+ o.setResultCode(GlobalErrorCodeConstants.SUCCESS.getCode());
});
- apiAccessLogMapper.insert(infApiAccessLogDO);
-
- // 下面几个都是不匹配的数据
- // userId 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setUserId(3344L)));
- // userType
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
- // applicationName 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setApplicationName("test")));
- // requestUrl 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setRequestUrl("bar")));
- // 构造一个早期时间 2021-02-06 00:00:00
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setBeginTime(buildLocalDateTime(2021, 2, 6))));
- // duration 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setDuration(100)));
- // resultCode 不同的
- apiAccessLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiAccessLogDO, logDO -> logDO.setResultCode(2)));
-
- // 构造调用参数
+ apiAccessLogMapper.insert(apiAccessLogDO);
+ // 测试 userId 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setUserId(3344L)));
+ // 测试 userType 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setUserType(UserTypeEnum.MEMBER.getValue())));
+ // 测试 applicationName 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setApplicationName("test")));
+ // 测试 requestUrl 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setRequestUrl("bar")));
+ // 测试 beginTime 不匹配:构造一个早期时间 2021-02-06 00:00:00
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setBeginTime(buildTime(2021, 2, 6))));
+ // 测试 duration 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setDuration(100)));
+ // 测试 resultCode 不匹配
+ apiAccessLogMapper.insert(cloneIgnoreId(apiAccessLogDO, o -> o.setResultCode(2)));
+ // 准备参数
ApiAccessLogExportReqVO reqVO = new ApiAccessLogExportReqVO();
- reqVO.setUserId(userId);
- reqVO.setUserType(userType);
- reqVO.setApplicationName(applicationName);
- reqVO.setRequestUrl(requestUrl);
- reqVO.setBeginTime((new LocalDateTime[]{buildLocalDateTime(2021, 3, 12),buildLocalDateTime(2021, 3, 14)}));
- reqVO.setDuration(duration);
- reqVO.setResultCode(resultCode);
+ reqVO.setUserId(2233L);
+ reqVO.setUserType(UserTypeEnum.ADMIN.getValue());
+ reqVO.setApplicationName("yudao-test");
+ reqVO.setRequestUrl("foo");
+ reqVO.setBeginTime(buildBetweenTime(2021, 3, 13, 2021, 3, 13));
+ reqVO.setDuration(1000);
+ reqVO.setResultCode(GlobalErrorCodeConstants.SUCCESS.getCode());
- // 调用service方法
+ // 调用
List list = apiAccessLogService.getApiAccessLogList(reqVO);
-
// 断言,只查到了一条符合条件的
assertEquals(1, list.size());
- assertPojoEquals(infApiAccessLogDO, list.get(0));
+ assertPojoEquals(apiAccessLogDO, list.get(0));
}
@Test
- public void testCreateApiAccessLogAsync() {
+ public void testCreateApiAccessLog() {
// 准备参数
- ApiAccessLogCreateReqDTO createDTO = RandomUtils.randomPojo(ApiAccessLogCreateReqDTO.class,
- dto -> dto.setUserType(RandomUtil.randomEle(UserTypeEnum.values()).getValue()));
+ ApiAccessLogCreateReqDTO createDTO = randomPojo(ApiAccessLogCreateReqDTO.class);
// 调用
apiAccessLogService.createApiAccessLog(createDTO);
// 断言
- ApiAccessLogDO infApiAccessLogDO = apiAccessLogMapper.selectOne(null);
- assertNotNull(infApiAccessLogDO);
- assertPojoEquals(createDTO, infApiAccessLogDO);
+ ApiAccessLogDO apiAccessLogDO = apiAccessLogMapper.selectOne(null);
+ assertPojoEquals(createDTO, apiAccessLogDO);
}
-
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImplTest.java b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImplTest.java
index bffdf46e8..86e55f5d1 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImplTest.java
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/java/cn/iocoder/yudao/module/infra/service/logger/ApiErrorLogServiceImplTest.java
@@ -1,28 +1,28 @@
package cn.iocoder.yudao.module.infra.service.logger;
-import cn.hutool.core.util.RandomUtil;
import cn.iocoder.yudao.framework.common.enums.UserTypeEnum;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
-import cn.iocoder.yudao.framework.common.util.object.ObjectUtils;
import cn.iocoder.yudao.framework.test.core.ut.BaseDbUnitTest;
-import cn.iocoder.yudao.framework.test.core.util.RandomUtils;
import cn.iocoder.yudao.module.infra.api.logger.dto.ApiErrorLogCreateReqDTO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apierrorlog.ApiErrorLogExportReqVO;
import cn.iocoder.yudao.module.infra.controller.admin.logger.vo.apierrorlog.ApiErrorLogPageReqVO;
import cn.iocoder.yudao.module.infra.dal.dataobject.logger.ApiErrorLogDO;
import cn.iocoder.yudao.module.infra.dal.mysql.logger.ApiErrorLogMapper;
import cn.iocoder.yudao.module.infra.enums.logger.ApiErrorLogProcessStatusEnum;
-import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import org.springframework.context.annotation.Import;
import javax.annotation.Resource;
-import java.time.LocalDateTime;
import java.util.List;
-import static cn.iocoder.yudao.framework.common.util.date.DateUtils.buildLocalDateTime;
+import static cn.hutool.core.util.RandomUtil.randomEle;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildBetweenTime;
+import static cn.iocoder.yudao.framework.common.util.date.LocalDateTimeUtils.buildTime;
+import static cn.iocoder.yudao.framework.common.util.object.ObjectUtils.cloneIgnoreId;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
+import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomLongId;
+import static cn.iocoder.yudao.framework.test.core.util.RandomUtils.randomPojo;
import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.API_ERROR_LOG_NOT_FOUND;
import static cn.iocoder.yudao.module.infra.enums.ErrorCodeConstants.API_ERROR_LOG_PROCESSED;
import static org.junit.jupiter.api.Assertions.assertEquals;
@@ -35,161 +35,150 @@ public class ApiErrorLogServiceImplTest extends BaseDbUnitTest {
private ApiErrorLogServiceImpl apiErrorLogService;
@Resource
- private ApiErrorLogMapper infApiErrorLogMapper;
+ private ApiErrorLogMapper apiErrorLogMapper;
@Test
public void testGetApiErrorLogPage() {
- // 构造测试数据
- long userId = 2233L;
- int userType = UserTypeEnum.ADMIN.getValue();
- String applicationName = "yudao-test";
- String requestUrl = "foo";
- LocalDateTime beginTime = buildLocalDateTime(2021, 3, 13);
- int progressStatus = ApiErrorLogProcessStatusEnum.INIT.getStatus();
-
- ApiErrorLogDO infApiErrorLogDO = RandomUtils.randomPojo(ApiErrorLogDO.class, logDO -> {
- logDO.setUserId(userId);
- logDO.setUserType(userType);
- logDO.setApplicationName(applicationName);
- logDO.setRequestUrl(requestUrl);
- logDO.setExceptionTime(beginTime);
- logDO.setProcessStatus(progressStatus);
+ // mock 数据
+ ApiErrorLogDO apiErrorLogDO = randomPojo(ApiErrorLogDO.class, o -> {
+ o.setUserId(2233L);
+ o.setUserType(UserTypeEnum.ADMIN.getValue());
+ o.setApplicationName("yudao-test");
+ o.setRequestUrl("foo");
+ o.setExceptionTime(buildTime(2021, 3, 13));
+ o.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
});
- infApiErrorLogMapper.insert(infApiErrorLogDO);
-
- // 下面几个都是不匹配的数据
- // userId 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setUserId(3344L)));
- // userType
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
- // applicationName 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setApplicationName("test")));
- // requestUrl 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setRequestUrl("bar")));
- // 构造一个早期时间 2021-02-06 00:00:00
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setExceptionTime(buildLocalDateTime(2021, 2, 6))));
- // progressStatus 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus())));
-
- // 构造调用参数
+ apiErrorLogMapper.insert(apiErrorLogDO);
+ // 测试 userId 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, o -> o.setUserId(3344L)));
+ // 测试 userType 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
+ // 测试 applicationName 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setApplicationName("test")));
+ // 测试 requestUrl 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setRequestUrl("bar")));
+ // 测试 exceptionTime 不匹配:构造一个早期时间 2021-02-06 00:00:00
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setExceptionTime(buildTime(2021, 2, 6))));
+ // 测试 progressStatus 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus())));
+ // 准备参数
ApiErrorLogPageReqVO reqVO = new ApiErrorLogPageReqVO();
- reqVO.setUserId(userId);
- reqVO.setUserType(userType);
- reqVO.setApplicationName(applicationName);
- reqVO.setRequestUrl(requestUrl);
- reqVO.setExceptionTime((new LocalDateTime[]{buildLocalDateTime(2021, 3, 12),buildLocalDateTime(2021, 3, 14)}));
- reqVO.setProcessStatus(progressStatus);
+ reqVO.setUserId(2233L);
+ reqVO.setUserType(UserTypeEnum.ADMIN.getValue());
+ reqVO.setApplicationName("yudao-test");
+ reqVO.setRequestUrl("foo");
+ reqVO.setExceptionTime(buildBetweenTime(2021, 3, 1, 2021, 3, 31));
+ reqVO.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
- // 调用service方法
+ // 调用
PageResult pageResult = apiErrorLogService.getApiErrorLogPage(reqVO);
-
// 断言,只查到了一条符合条件的
assertEquals(1, pageResult.getTotal());
assertEquals(1, pageResult.getList().size());
- assertPojoEquals(infApiErrorLogDO, pageResult.getList().get(0));
+ assertPojoEquals(apiErrorLogDO, pageResult.getList().get(0));
}
@Test
public void testGetApiErrorLogList() {
- // 构造测试数据
- long userId = 2233L;
- int userType = UserTypeEnum.ADMIN.getValue();
- String applicationName = "yudao-test";
- String requestUrl = "foo";
- LocalDateTime beginTime = buildLocalDateTime(2021, 3, 13);
- int progressStatus = ApiErrorLogProcessStatusEnum.INIT.getStatus();
-
- ApiErrorLogDO infApiErrorLogDO = RandomUtils.randomPojo(ApiErrorLogDO.class, logDO -> {
- logDO.setUserId(userId);
- logDO.setUserType(userType);
- logDO.setApplicationName(applicationName);
- logDO.setRequestUrl(requestUrl);
- logDO.setExceptionTime(beginTime);
- logDO.setProcessStatus(progressStatus);
+ // mock 数据
+ ApiErrorLogDO apiErrorLogDO = randomPojo(ApiErrorLogDO.class, o -> {
+ o.setUserId(2233L);
+ o.setUserType(UserTypeEnum.ADMIN.getValue());
+ o.setApplicationName("yudao-test");
+ o.setRequestUrl("foo");
+ o.setExceptionTime(buildTime(2021, 3, 13));
+ o.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
});
- infApiErrorLogMapper.insert(infApiErrorLogDO);
-
- // 下面几个都是不匹配的数据
- // userId 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setUserId(3344L)));
- // userType
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
- // applicationName 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setApplicationName("test")));
- // requestUrl 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setRequestUrl("bar")));
- // 构造一个早期时间 2021-02-06 00:00:00
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setExceptionTime(buildLocalDateTime(2021, 2, 6))));
- // progressStatus 不同的
- infApiErrorLogMapper.insert(ObjectUtils.cloneIgnoreId(infApiErrorLogDO, logDO -> logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus())));
-
- // 构造调用参数
+ apiErrorLogMapper.insert(apiErrorLogDO);
+ // 测试 userId 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, o -> o.setUserId(3344L)));
+ // 测试 userType 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setUserType(UserTypeEnum.MEMBER.getValue())));
+ // 测试 applicationName 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setApplicationName("test")));
+ // 测试 requestUrl 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setRequestUrl("bar")));
+ // 测试 exceptionTime 不匹配:构造一个早期时间 2021-02-06 00:00:00
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setExceptionTime(buildTime(2021, 2, 6))));
+ // 测试 progressStatus 不匹配
+ apiErrorLogMapper.insert(cloneIgnoreId(apiErrorLogDO, logDO -> logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus())));
+ // 准备参数
ApiErrorLogExportReqVO reqVO = new ApiErrorLogExportReqVO();
- reqVO.setUserId(userId);
- reqVO.setUserType(userType);
- reqVO.setApplicationName(applicationName);
- reqVO.setRequestUrl(requestUrl);
- reqVO.setExceptionTime((new LocalDateTime[]{buildLocalDateTime(2021, 3, 12),buildLocalDateTime(2021, 3, 14)}));
- reqVO.setProcessStatus(progressStatus);
+ reqVO.setUserId(2233L);
+ reqVO.setUserType(UserTypeEnum.ADMIN.getValue());
+ reqVO.setApplicationName("yudao-test");
+ reqVO.setRequestUrl("foo");
+ reqVO.setExceptionTime(buildBetweenTime(2021, 3, 1, 2021, 3, 31));
+ reqVO.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
- // 调用service方法
+ // 调用
List list = apiErrorLogService.getApiErrorLogList(reqVO);
-
// 断言,只查到了一条符合条件的
assertEquals(1, list.size());
- assertPojoEquals(infApiErrorLogDO, list.get(0));
- }
-
-
- // TODO 芋艿:单元测试,可以拆小一点
- @Test
- public void testUpdateApiErrorLogProcess() {
- // 先构造两条数据,第一条用于抛出异常,第二条用于正常的执行update操作
- Long processUserId = 2233L;
-
- ApiErrorLogDO first = RandomUtils.randomPojo(ApiErrorLogDO.class, logDO -> {
- logDO.setProcessUserId(processUserId);
- logDO.setUserType(UserTypeEnum.ADMIN.getValue());
- logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus());
- });
- infApiErrorLogMapper.insert(first);
-
- ApiErrorLogDO second = RandomUtils.randomPojo(ApiErrorLogDO.class, logDO -> {
- logDO.setProcessUserId(1122L);
- logDO.setUserType(UserTypeEnum.ADMIN.getValue());
- logDO.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus());
- });
- infApiErrorLogMapper.insert(second);
-
- Long firstId = first.getId();
- Long secondId = second.getId();
-
- // 执行正常的 update 操作
- apiErrorLogService.updateApiErrorLogProcess(secondId, ApiErrorLogProcessStatusEnum.DONE.getStatus(), processUserId);
- ApiErrorLogDO secondSelect = infApiErrorLogMapper.selectOne("id", secondId);
-
- // id 为 0 查询不到,应该抛出异常 API_ERROR_LOG_NOT_FOUND
- assertServiceException(() -> apiErrorLogService.updateApiErrorLogProcess(0L, ApiErrorLogProcessStatusEnum.DONE.getStatus(), processUserId), API_ERROR_LOG_NOT_FOUND);
- // id 为 first 的 progressStatus 为 DONE ,应该抛出 API_ERROR_LOG_PROCESSED
- assertServiceException(() -> apiErrorLogService.updateApiErrorLogProcess(firstId, ApiErrorLogProcessStatusEnum.DONE.getStatus(), processUserId), API_ERROR_LOG_PROCESSED);
- // 验证 progressStatus 是否修改成功
- Assertions.assertEquals(ApiErrorLogProcessStatusEnum.DONE.getStatus(), secondSelect.getProcessStatus());
- // 验证 progressUserId 是否修改成功
- Assertions.assertEquals(processUserId, secondSelect.getProcessUserId());
+ assertPojoEquals(apiErrorLogDO, list.get(0));
}
@Test
- public void testCreateApiErrorLogAsync() {
+ public void testCreateApiErrorLog() {
// 准备参数
- ApiErrorLogCreateReqDTO createDTO = RandomUtils.randomPojo(ApiErrorLogCreateReqDTO.class,
- dto -> dto.setUserType(RandomUtil.randomEle(UserTypeEnum.values()).getValue()));
+ ApiErrorLogCreateReqDTO createDTO = randomPojo(ApiErrorLogCreateReqDTO.class);
// 调用
apiErrorLogService.createApiErrorLog(createDTO);
// 断言
- ApiErrorLogDO infApiErrorLogDO = infApiErrorLogMapper.selectOne(null);
- assertNotNull(infApiErrorLogDO);
- assertPojoEquals(createDTO, infApiErrorLogDO);
+ ApiErrorLogDO apiErrorLogDO = apiErrorLogMapper.selectOne(null);
+ assertPojoEquals(createDTO, apiErrorLogDO);
+ assertEquals(ApiErrorLogProcessStatusEnum.INIT.getStatus(), apiErrorLogDO.getProcessStatus());
+ }
+
+ @Test
+ public void testUpdateApiErrorLogProcess_success() {
+ // 准备参数
+ ApiErrorLogDO apiErrorLogDO = randomPojo(ApiErrorLogDO.class,
+ o -> o.setProcessStatus(ApiErrorLogProcessStatusEnum.INIT.getStatus()));
+ apiErrorLogMapper.insert(apiErrorLogDO);
+ // 准备参数
+ Long id = apiErrorLogDO.getId();
+ Integer processStatus = randomEle(ApiErrorLogProcessStatusEnum.values()).getStatus();
+ Long processUserId = randomLongId();
+
+ // 调用
+ apiErrorLogService.updateApiErrorLogProcess(id, processStatus, processUserId);
+ // 断言
+ ApiErrorLogDO dbApiErrorLogDO = apiErrorLogMapper.selectById(apiErrorLogDO.getId());
+ assertEquals(processStatus, dbApiErrorLogDO.getProcessStatus());
+ assertEquals(processUserId, dbApiErrorLogDO.getProcessUserId());
+ assertNotNull(dbApiErrorLogDO.getProcessTime());
+ }
+
+ @Test
+ public void testUpdateApiErrorLogProcess_processed() {
+ // 准备参数
+ ApiErrorLogDO apiErrorLogDO = randomPojo(ApiErrorLogDO.class,
+ o -> o.setProcessStatus(ApiErrorLogProcessStatusEnum.DONE.getStatus()));
+ apiErrorLogMapper.insert(apiErrorLogDO);
+ // 准备参数
+ Long id = apiErrorLogDO.getId();
+ Integer processStatus = randomEle(ApiErrorLogProcessStatusEnum.values()).getStatus();
+ Long processUserId = randomLongId();
+
+ // 调用,并断言异常
+ assertServiceException(() ->
+ apiErrorLogService.updateApiErrorLogProcess(id, processStatus, processUserId),
+ API_ERROR_LOG_PROCESSED);
+ }
+
+ @Test
+ public void testUpdateApiErrorLogProcess_notFound() {
+ // 准备参数
+ Long id = randomLongId();
+ Integer processStatus = randomEle(ApiErrorLogProcessStatusEnum.values()).getStatus();
+ Long processUserId = randomLongId();
+
+ // 调用,并断言异常
+ assertServiceException(() ->
+ apiErrorLogService.updateApiErrorLogProcess(id, processStatus, processUserId),
+ API_ERROR_LOG_NOT_FOUND);
}
}
diff --git a/yudao-module-infra/yudao-module-infra-biz/src/test/resources/sql/create_tables.sql b/yudao-module-infra/yudao-module-infra-biz/src/test/resources/sql/create_tables.sql
index 5825e0fef..9d4e57e67 100644
--- a/yudao-module-infra/yudao-module-infra-biz/src/test/resources/sql/create_tables.sql
+++ b/yudao-module-infra/yudao-module-infra-biz/src/test/resources/sql/create_tables.sql
@@ -1,9 +1,9 @@
CREATE TABLE IF NOT EXISTS "infra_config" (
- "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY,
+ "id" bigint(20) NOT NULL GENERATED BY DEFAULT AS IDENTITY COMMENT '编号',
"category" varchar(50) NOT NULL,
"type" tinyint NOT NULL,
- "name" varchar(100) NOT NULL DEFAULT '',
+ "name" varchar(100) NOT NULL DEFAULT '' COMMENT '名字',
"config_key" varchar(100) NOT NULL DEFAULT '',
"value" varchar(500) NOT NULL DEFAULT '',
"visible" bit NOT NULL,
diff --git a/yudao-module-report/pom.xml b/yudao-module-report/pom.xml
new file mode 100644
index 000000000..2c8aecedc
--- /dev/null
+++ b/yudao-module-report/pom.xml
@@ -0,0 +1,23 @@
+
+
+
+ cn.iocoder.cloud
+ yudao
+ ${revision}
+
+ 4.0.0
+
+ yudao-module-report-api
+ yudao-module-report-biz
+
+ yudao-module-report
+ pom
+
+ ${project.artifactId}
+
+ report 模块,主要实现数据可视化报表等功能。
+
+
+
diff --git a/yudao-module-report/yudao-module-report-api/pom.xml b/yudao-module-report/yudao-module-report-api/pom.xml
new file mode 100644
index 000000000..7d7135538
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-api/pom.xml
@@ -0,0 +1,26 @@
+
+
+
+ cn.iocoder.cloud
+ yudao-module-report
+ ${revision}
+
+ 4.0.0
+
+ yudao-module-report-api
+ jar
+
+ ${project.artifactId}
+
+ report 模块 API,暴露给其它模块调用
+
+
+
+
+ cn.iocoder.cloud
+ yudao-common
+
+
+
diff --git a/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java
new file mode 100644
index 000000000..827bef3fd
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/api/package-info.java
@@ -0,0 +1,4 @@
+/**
+ * 占位,避免 api 目录无文件时,git 无法提交
+ */
+package cn.iocoder.yudao.module.report.api;
diff --git a/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java
new file mode 100644
index 000000000..d90bed398
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-api/src/main/java/cn/iocoder/yudao/module/report/enums/ErrorCodeConstants.java
@@ -0,0 +1,15 @@
+package cn.iocoder.yudao.module.report.enums;
+
+import cn.iocoder.yudao.framework.common.exception.ErrorCode;
+
+/**
+ * Report 错误码枚举类
+ *
+ * system 系统,使用 1-003-000-000 段
+ */
+public interface ErrorCodeConstants {
+
+ // ========== AUTH 模块 1003000000 ==========
+ ErrorCode GO_VIEW_PROJECT_NOT_EXISTS = new ErrorCode(1003000000, "GoView 项目不存在");
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/pom.xml b/yudao-module-report/yudao-module-report-biz/pom.xml
new file mode 100644
index 000000000..2b1349650
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/pom.xml
@@ -0,0 +1,135 @@
+
+
+
+ cn.iocoder.cloud
+ yudao-module-report
+ ${revision}
+
+ 4.0.0
+
+ yudao-module-report-biz
+ jar
+
+ ${project.artifactId}
+
+ report 模块,主要实现数据可视化报表等功能:
+ 1. 基于「积木报表」实现,打印设计、报表设计、图形设计、大屏设计等。
+
+
+
+
+ org.springframework.cloud
+ spring-cloud-starter-bootstrap
+
+
+
+
+ cn.iocoder.cloud
+ yudao-module-report-api
+ ${revision}
+
+
+
+ cn.iocoder.cloud
+ yudao-module-system-api
+ ${revision}
+
+
+ cn.iocoder.cloud
+ yudao-module-infra-api
+ ${revision}
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-banner
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-biz-operatelog
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-biz-tenant
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-biz-error-code
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-security
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-mybatis
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-redis
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-rpc
+
+
+
+
+ com.alibaba.cloud
+ spring-cloud-starter-alibaba-nacos-discovery
+
+
+
+
+ com.alibaba.cloud
+ spring-cloud-starter-alibaba-nacos-config
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-test
+ test
+
+
+
+
+ cn.iocoder.cloud
+ yudao-spring-boot-starter-monitor
+
+
+
+
+ org.jeecgframework.jimureport
+ jimureport-spring-boot-starter
+
+
+
+ xerces
+ xercesImpl
+
+
+
+
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/ReportServerApplication.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/ReportServerApplication.java
new file mode 100644
index 000000000..759482a31
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/ReportServerApplication.java
@@ -0,0 +1,30 @@
+package cn.iocoder.yudao.module.report;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+
+/**
+ * 项目的启动类
+ *
+ * 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ * 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ * 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ *
+ * @author 芋道源码
+ */
+@SpringBootApplication
+public class ReportServerApplication {
+
+ public static void main(String[] args) {
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+
+ SpringApplication.run(ReportServerApplication.class, args);
+
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ // 如果你碰到启动的问题,请认真阅读 https://cloud.iocoder.cn/quick-start/ 文章
+ }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java
new file mode 100644
index 000000000..e32b8b916
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/ajreport/package-info.java
@@ -0,0 +1 @@
+package cn.iocoder.yudao.module.report.controller.admin.ajreport;
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java
new file mode 100644
index 000000000..31805c1e2
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewDataController.java
@@ -0,0 +1,65 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview;
+
+import cn.hutool.core.map.MapUtil;
+import cn.hutool.core.util.RandomUtil;
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.operatelog.core.annotations.OperateLog;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataGetBySqlReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.data.GoViewDataRespVO;
+import cn.iocoder.yudao.module.report.service.goview.GoViewDataService;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.RequestBody;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestParam;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+import java.util.Arrays;
+import java.util.LinkedList;
+import java.util.Map;
+
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+
+//@Tag(name = "管理后台 - GoView 数据", description = "提供 SQL、HTTP 等数据查询的能力")
+@RestController
+@RequestMapping("/report/go-view/data")
+@Validated
+public class GoViewDataController {
+
+ @Resource
+ private GoViewDataService goViewDataService;
+
+ @RequestMapping("/get-by-sql")
+// @Operation(summary = "使用 SQL 查询数据")
+ @PreAuthorize("@ss.hasPermission('report:go-view-data:get-by-sql')")
+ @OperateLog(enable = false) // 不记录操作日志,因为不需要
+ public CommonResult getDataBySQL(@Valid @RequestBody GoViewDataGetBySqlReqVO reqVO) {
+ return success(goViewDataService.getDataBySQL(reqVO.getSql()));
+ }
+
+ @RequestMapping("/get-by-http")
+// @Operation(summary = "使用 HTTP 查询数据", description = "这个只是示例接口,实际应该每个查询,都要写一个接口")
+ @PreAuthorize("@ss.hasPermission('report:go-view-data:get-by-http')")
+ @OperateLog(enable = false) // 不记录操作日志,因为不需要
+ public CommonResult getDataByHttp(
+ @RequestParam(required = false) Map params,
+ @RequestBody(required = false) String body) { // params、body 按照需要去接收,这里仅仅是示例
+ GoViewDataRespVO respVO = new GoViewDataRespVO();
+ // 1. 数据维度
+ respVO.setDimensions(Arrays.asList("日期", "PV", "UV")); // PV 是每天访问次数;UV 是每天访问人数
+ // 2. 明细数据列表
+ // 目前通过随机的方式生成。一般来说,这里你可以写逻辑来实现数据的返回
+ respVO.setSource(new LinkedList<>());
+ for (int i = 1; i <= 12; i++) {
+ String date = "2021-" + (i < 10 ? "0" + i : i);
+ Integer pv = RandomUtil.randomInt(1000, 10000);
+ Integer uv = RandomUtil.randomInt(100, 1000);
+ respVO.getSource().add(MapUtil.builder().put("日期", date)
+ .put("PV", pv).put("UV", uv).build());
+ }
+ return success(respVO);
+ }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java
new file mode 100644
index 000000000..240be46c3
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/GoViewProjectController.java
@@ -0,0 +1,73 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview;
+
+import cn.iocoder.yudao.framework.common.pojo.CommonResult;
+import cn.iocoder.yudao.framework.common.pojo.PageParam;
+import cn.iocoder.yudao.framework.common.pojo.PageResult;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectCreateReqVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectRespVO;
+import cn.iocoder.yudao.module.report.controller.admin.goview.vo.project.GoViewProjectUpdateReqVO;
+import cn.iocoder.yudao.module.report.convert.goview.GoViewProjectConvert;
+import cn.iocoder.yudao.module.report.dal.dataobject.goview.GoViewProjectDO;
+import cn.iocoder.yudao.module.report.service.goview.GoViewProjectService;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+
+import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
+import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils.getLoginUserId;
+
+//@Tag(name = "管理后台 - GoView 项目")
+@RestController
+@RequestMapping("/report/go-view/project")
+@Validated
+public class GoViewProjectController {
+
+ @Resource
+ private GoViewProjectService goViewProjectService;
+
+ @PostMapping("/create")
+// @Operation(summary = "创建项目")
+ @PreAuthorize("@ss.hasPermission('report:go-view-project:create')")
+ public CommonResult createProject(@Valid @RequestBody GoViewProjectCreateReqVO createReqVO) {
+ return success(goViewProjectService.createProject(createReqVO));
+ }
+
+ @PutMapping("/update")
+// @Operation(summary = "更新项目")
+ @PreAuthorize("@ss.hasPermission('report:go-view-project:update')")
+ public CommonResult updateProject(@Valid @RequestBody GoViewProjectUpdateReqVO updateReqVO) {
+ goViewProjectService.updateProject(updateReqVO);
+ return success(true);
+ }
+
+ @DeleteMapping("/delete")
+// @Operation(summary = "删除 GoView 项目")
+// @Parameter(name = "id", description = "编号", required = true, example = "1024")
+ @PreAuthorize("@ss.hasPermission('report:go-view-project:delete')")
+ public CommonResult deleteProject(@RequestParam("id") Long id) {
+ goViewProjectService.deleteProject(id);
+ return success(true);
+ }
+
+ @GetMapping("/get")
+// @Operation(summary = "获得项目")
+// @Parameter(name = "id", description = "编号", required = true, example = "1024")
+ @PreAuthorize("@ss.hasPermission('report:go-view-project:query')")
+ public CommonResult getProject(@RequestParam("id") Long id) {
+ GoViewProjectDO project = goViewProjectService.getProject(id);
+ return success(GoViewProjectConvert.INSTANCE.convert(project));
+ }
+
+ @GetMapping("/my-page")
+// @Operation(summary = "获得我的项目分页")
+ @PreAuthorize("@ss.hasPermission('report:go-view-project:query')")
+ public CommonResult> getMyProjectPage(@Valid PageParam pageVO) {
+ PageResult pageResult = goViewProjectService.getMyProjectPage(
+ pageVO, getLoginUserId());
+ return success(GoViewProjectConvert.INSTANCE.convertPage(pageResult));
+ }
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java
new file mode 100644
index 000000000..ecd1fdcd7
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataGetBySqlReqVO.java
@@ -0,0 +1,15 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.data;
+
+import lombok.Data;
+
+import javax.validation.constraints.NotEmpty;
+
+//@Schema(description = "管理后台 - GoView 使用 SQL 查询数据 Request VO")
+@Data
+public class GoViewDataGetBySqlReqVO {
+
+// @Schema(description = "SQL 语句", required = true, example = "SELECT * FROM user")
+ @NotEmpty(message = "SQL 语句不能为空")
+ private String sql;
+
+}
diff --git a/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java
new file mode 100644
index 000000000..25e4112e5
--- /dev/null
+++ b/yudao-module-report/yudao-module-report-biz/src/main/java/cn/iocoder/yudao/module/report/controller/admin/goview/vo/data/GoViewDataRespVO.java
@@ -0,0 +1,19 @@
+package cn.iocoder.yudao.module.report.controller.admin.goview.vo.data;
+
+//import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import java.util.List;
+import java.util.Map;
+
+//@Schema(description = "管理后台 - GoView 数据 Response VO")
+@Data
+public class GoViewDataRespVO {
+
+// @Schema(description = "数据维度", required = true, example = "['product', 'data1', 'data2']")
+ private List dimensions;
+
+// @Schema(description = "数据明细列表", required = true)
+ private List