diff --git a/src/main/java/com/example/demo/common/typography/BaseServiceImpl.java b/src/main/java/com/example/demo/common/typography/BaseServiceImpl.java index 7421621..8e5aa13 100644 --- a/src/main/java/com/example/demo/common/typography/BaseServiceImpl.java +++ b/src/main/java/com/example/demo/common/typography/BaseServiceImpl.java @@ -3,20 +3,26 @@ package com.example.demo.common.typography; import cn.hutool.core.bean.BeanUtil; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.util.ObjectUtil; +import cn.hutool.core.util.StrUtil; +import cn.hutool.core.util.ZipUtil; import cn.zhxu.bs.BeanSearcher; import cn.zhxu.bs.SearchResult; import cn.zhxu.bs.operator.Contain; import cn.zhxu.bs.util.MapUtils; +import com.alibaba.fastjson2.JSON; +import com.alibaba.fastjson2.JSONObject; import com.example.demo.common.constant.GlobalConstants; import com.example.demo.common.domain.BaseDTO; import com.example.demo.common.domain.BaseEntity; import com.example.demo.common.domain.BaseQueryDTO; import com.example.demo.common.domain.BaseVO; +import com.example.demo.common.exception.BusinessException; import com.fhs.trans.service.impl.TransService; import com.mybatisflex.core.BaseMapper; import com.mybatisflex.spring.service.impl.ServiceImpl; import jakarta.annotation.PostConstruct; import jakarta.annotation.PreDestroy; +import jakarta.servlet.http.HttpServletResponse; import lombok.RequiredArgsConstructor; import org.slf4j.Logger; import org.springframework.beans.factory.DisposableBean; @@ -24,8 +30,12 @@ import org.springframework.beans.factory.InitializingBean; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; +import java.io.IOException; +import java.io.InputStream; import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; +import java.util.ArrayList; +import java.util.HashMap; import java.util.List; import java.util.Map; @@ -59,6 +69,9 @@ public abstract class BaseServiceImpl< /** 实际业务实现VO类 */ private final Class clazzVO; + /** 实际业务实现Entity类 */ + private final Class clazzEntity; + /** 提供Select服务 */ private final BeanSearcher beanSearcher; @@ -164,12 +177,160 @@ public abstract class BaseServiceImpl< return wordVO; } + @Override + public Object importDetail(String line) { + log.warn("导入细节(暂无实现)"); + JSONObject jsonObject = JSON.parseObject(line); + jsonObject.get("ts"); + jsonObject.get(""); + Entity entity = JSON.parseObject(line, clazzEntity); + Map result = new HashMap<>(); + + // 默认导入失败 + result.put("state", "error"); + if(ObjectUtil.isNotEmpty(detail(entity.getId()))) { + result.put("id", entity.getId()); + if(StrUtil.isNotBlank(entity.getName())) { + result.put("name", entity.getName()); + } + return result; + } + + // TODO 解密,校验完整性 + + // 设置默认值 + if (entity.getIsDeleted() == null) { + entity.setIsDeleted(Integer.valueOf(GlobalConstants.N)); + } + + // 保存到数据库 + boolean flag = save(entity); + if (flag) { + result.put("state", "success"); + } + return null; + } + + @Override + public Object exportDetail(String id) { + log.warn("导出细节(暂无实现)"); + return null; + } + @Override public void refreshCache() { // ignore log.warn("刷新缓存(暂无实现)"); } + @Override + public Map importJSONLData(String content) { + Map result = new HashMap<>(); + int successCount = 0; + int failCount = 0; + List errors = new ArrayList<>(); + + try { + // 按行分割JSONL数据 + String[] lines = content.split("\n"); + + for (int i = 0; i < lines.length; i++) { + String line = lines[i].trim(); + if (line.isEmpty()) continue; + + try { + // 解析每一行JSON为Entity对象 + // 使用try-catch块忽略无法转化的数据,继续处理下一行 + importDetail(line); + successCount++; + } catch (Exception e) { + // 记录失败信息但继续处理下一行数据 + failCount++; + errors.add("第" + (i + 1) + "行导入失败: " + e.getMessage()); + log.warn("忽略无法解析的JSON数据行[{}]: {}", i + 1, line); + // 继续处理下一行,不抛出异常中断整体流程 + continue; + } + } + + result.put("successCount", String.valueOf(successCount)); + result.put("failCount", String.valueOf(failCount)); + result.put("errors", String.join("\n", errors)); + result.put("message", "导入完成,成功 " + successCount + " 条,失败 " + failCount + " 条"); + + } catch (Exception e) { + result.put("error", "解析JSONL数据失败: " + e.getMessage()); + result.put("successCount", "0"); + result.put("failCount", "0"); + result.put("message", "导入失败"); + } + + return result; + } + + @Override + public void exportJSONLData(HttpServletResponse response, List ids) { + try { + if (ids == null || ids.isEmpty()) { + throw new BusinessException("导出ID列表不能为空"); + } + + // 验证并获取所有要导出的数据 + List list = new ArrayList<>(); + for (String id : ids) { + try { + // 使用detail方法验证ID是否存在,并获取数据 + Object templateVO = exportDetail(id); + if (templateVO == null) { + throw new BusinessException("不存在: " + id); + } + // 添加到导出列表 + list.add(templateVO); + } catch (Exception e) { + // ignore + } + } + // 准备文件流和文件名列表用于压缩 + List fileNameUniqueList = new ArrayList<>(); + List inputStreams = new ArrayList<>(); + + // 创建一个JSONL文件,包含所有模板数据,每行一个JSON对象 + StringBuilder jsonlContent = new StringBuilder(); + for (Object object : list) { + String jsonContent = JSON.toJSONString(object); + // TODO 加密 + jsonlContent.append(jsonContent).append("\n"); + } + // 转换为数组 + String[] fileNamesArr = fileNameUniqueList.toArray(new String[0]); + InputStream[] inputStreamsArr = inputStreams.toArray(new InputStream[0]); + + // 使用ZipUtil进行压缩下载 + try { + ZipUtil.zip(response.getOutputStream(), fileNamesArr, inputStreamsArr); + } catch (IOException e) { + throw new BusinessException("压缩下载失败: " + e.getMessage()); + } finally { + // 关闭所有输入流 + for (InputStream inputStream : inputStreams) { + try { + if (inputStream != null) { + inputStream.close(); + } + } catch (IOException e) { + // 忽略关闭流的异常 + } + } + } + + } catch (BusinessException e) { + // 直接抛出业务异常,保留原始错误信息 + throw e; + } catch (Exception e) { + throw new BusinessException("导出JSONL数据失败: " + e.getMessage()); + } + } + @PostConstruct public void init() { // ignore @@ -270,4 +431,29 @@ public abstract class BaseServiceImpl< ParameterizedType parameterizedType = (ParameterizedType) superClass; return (Class) parameterizedType.getActualTypeArguments()[2]; } + + /** + * 确保密钥字节数组为指定长度 + * @param key 原始密钥字符串 + * @param length 所需长度 + * @return 调整后的密钥字节数组 + */ + private static byte[] ensureKeyLength(String key, int length) { + byte[] keyBytes = key.getBytes(java.nio.charset.StandardCharsets.UTF_8); + if (keyBytes.length == length) { + return keyBytes; + } else if (keyBytes.length > length) { + // 如果太长则截取 + byte[] result = new byte[length]; + System.arraycopy(keyBytes, 0, result, 0, length); + return result; + } else { + // 如果太短则填充0(或者您可以选择其他填充方式) + byte[] result = new byte[length]; + System.arraycopy(keyBytes, 0, result, 0, keyBytes.length); + // 剩余部分默认为0 + return result; + } + } + } diff --git a/src/main/java/com/example/demo/parser/service/impl/ConditionMapServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/ConditionMapServiceImpl.java index 49b3636..e3e18f3 100644 --- a/src/main/java/com/example/demo/parser/service/impl/ConditionMapServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/ConditionMapServiceImpl.java @@ -37,7 +37,11 @@ public class ConditionMapServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, ConditionMapServiceImpl.class.getSimpleName(), ConditionMapVO.class, beanSearcher, transService); + super(log, + ConditionMapServiceImpl.class.getSimpleName(), + ConditionMapVO.class, + ConditionMapEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/ConfigDocumentServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/ConfigDocumentServiceImpl.java index 505e598..1626eed 100644 --- a/src/main/java/com/example/demo/parser/service/impl/ConfigDocumentServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/ConfigDocumentServiceImpl.java @@ -37,7 +37,11 @@ public class ConfigDocumentServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, ConfigDocumentServiceImpl.class.getSimpleName(), ConfigDocumentVO.class, beanSearcher, transService); + super(log, + ConfigDocumentServiceImpl.class.getSimpleName(), + ConfigDocumentVO.class, + ConfigDocumentEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/ConfigValueServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/ConfigValueServiceImpl.java index 187b24f..a388cee 100644 --- a/src/main/java/com/example/demo/parser/service/impl/ConfigValueServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/ConfigValueServiceImpl.java @@ -37,7 +37,11 @@ public class ConfigValueServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, ConfigValueServiceImpl.class.getSimpleName(), ConfigValueVO.class, beanSearcher, transService); + super(log, + ConfigValueServiceImpl.class.getSimpleName(), + ConfigValueVO.class, + ConfigValueEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/FileRecordServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/FileRecordServiceImpl.java index c0bcc4d..8073afb 100644 --- a/src/main/java/com/example/demo/parser/service/impl/FileRecordServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/FileRecordServiceImpl.java @@ -37,6 +37,10 @@ public class FileRecordServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, FileRecordServiceImpl.class.getSimpleName(), FileRecordVO.class, beanSearcher, transService); + super(log, + FileRecordServiceImpl.class.getSimpleName(), + FileRecordVO.class, + FileRecordEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/LevelConfigServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/LevelConfigServiceImpl.java index 5b5ffe1..5e4aad6 100644 --- a/src/main/java/com/example/demo/parser/service/impl/LevelConfigServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/LevelConfigServiceImpl.java @@ -37,7 +37,11 @@ public class LevelConfigServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, LevelConfigServiceImpl.class.getSimpleName(), LevelConfigVO.class, beanSearcher, transService); + super(log, + LevelConfigServiceImpl.class.getSimpleName(), + LevelConfigVO.class, + LevelConfigEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/MapperRuleServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/MapperRuleServiceImpl.java index 7541d06..8a6a2b3 100644 --- a/src/main/java/com/example/demo/parser/service/impl/MapperRuleServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/MapperRuleServiceImpl.java @@ -38,7 +38,11 @@ public class MapperRuleServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, MapperRuleServiceImpl.class.getSimpleName(), MapperRuleVO.class, beanSearcher, transService); + super(log, + MapperRuleServiceImpl.class.getSimpleName(), + MapperRuleVO.class, + MapperRuleEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/ParseRuleServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/ParseRuleServiceImpl.java index 77c59c0..d362f27 100644 --- a/src/main/java/com/example/demo/parser/service/impl/ParseRuleServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/ParseRuleServiceImpl.java @@ -38,7 +38,11 @@ public class ParseRuleServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, ParseRuleServiceImpl.class.getSimpleName(), ParseRuleVO.class, beanSearcher, transService); + super(log, + ParseRuleServiceImpl.class.getSimpleName(), + ParseRuleVO.class, + ParseRuleEntity.class, + beanSearcher, transService); } } \ No newline at end of file diff --git a/src/main/java/com/example/demo/parser/service/impl/ValueConfigServiceImpl.java b/src/main/java/com/example/demo/parser/service/impl/ValueConfigServiceImpl.java index 77ffb80..4d2d89c 100644 --- a/src/main/java/com/example/demo/parser/service/impl/ValueConfigServiceImpl.java +++ b/src/main/java/com/example/demo/parser/service/impl/ValueConfigServiceImpl.java @@ -37,7 +37,11 @@ public class ValueConfigServiceImpl BeanSearcher beanSearcher, TransService transService ) { - super(log, ValueConfigServiceImpl.class.getSimpleName(), ValueConfigVO.class, beanSearcher, transService); + super(log, + ValueConfigServiceImpl.class.getSimpleName(), + ValueConfigVO.class, + ValueConfigEntity.class, + beanSearcher, transService); } } \ No newline at end of file