离线端数据包,文件解析

This commit is contained in:
dxfeng 2025-03-28 16:36:12 +08:00
parent 7dd3671dd2
commit 7ed94f0c7d
3 changed files with 232 additions and 59 deletions

View File

@ -15,7 +15,7 @@ import lombok.NoArgsConstructor;
@NoArgsConstructor @NoArgsConstructor
@Builder @Builder
public class FileConfig { public class FileConfig {
private String filedName; private String fieldName;
private String fileId; private String fileId;
private String isFilled; private String isFilled;
} }

View File

@ -2,9 +2,7 @@ package com.engine.secret.service.impl;
import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSON;
import com.engine.core.impl.Service; import com.engine.core.impl.Service;
import com.engine.secret.entity.unpack.DataConfig; import com.engine.secret.entity.unpack.*;
import com.engine.secret.entity.unpack.DataConfigDetail;
import com.engine.secret.entity.unpack.FileConfig;
import com.engine.secret.exception.CustomizeRunTimeException; import com.engine.secret.exception.CustomizeRunTimeException;
import com.engine.secret.service.QualificationApplicationService; import com.engine.secret.service.QualificationApplicationService;
import com.engine.secret.util.ModeUtil; import com.engine.secret.util.ModeUtil;
@ -19,7 +17,10 @@ import org.apache.commons.lang.StringUtils;
import weaver.conn.RecordSet; import weaver.conn.RecordSet;
import weaver.file.ImageFileManager; import weaver.file.ImageFileManager;
import weaver.formmode.IgnoreCaseHashMap; import weaver.formmode.IgnoreCaseHashMap;
import weaver.general.BaseBean;
import weaver.general.GCONST;
import java.io.File;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.nio.file.Files; import java.nio.file.Files;
@ -27,6 +28,7 @@ import java.nio.file.Path;
import java.nio.file.Paths; import java.nio.file.Paths;
import java.nio.file.StandardCopyOption; import java.nio.file.StandardCopyOption;
import java.util.*; import java.util.*;
import java.util.stream.Collectors;
/** /**
* @author:dxfeng * @author:dxfeng
@ -35,10 +37,22 @@ import java.util.*;
*/ */
public class QualificationApplicationServiceImpl extends Service implements QualificationApplicationService { public class QualificationApplicationServiceImpl extends Service implements QualificationApplicationService {
private static String UNZIP_PWD = "zizhi102!";
private static int UPLOAD_CATALOGUE = 122;
private static String CONFIG_TABLE_NAME = "uf_bmj_sjjxpz"; private static String CONFIG_TABLE_NAME = "uf_bmj_sjjxpz";
private static String CONFIG_DETAIL_TABLE_NAME = "uf_bmj_sjjxpz_dt1"; private static String CONFIG_DETAIL_TABLE_NAME = "uf_bmj_sjjxpz_dt1";
private static String FILE_DETAIL_TABLE_NAME = "uf_bmj_sjjxpz_dt2"; private static String FILE_DETAIL_TABLE_NAME = "uf_bmj_sjjxpz_dt2";
BaseBean baseBean = new BaseBean();
Map<String, List<ApplicationResource>> applicationResourceMap;
Map<String, Map<String, ResourceInfo>> resourceInfoMap;
Map<String, Integer> imageFileMap;
@Override @Override
public Map<String, Object> parsingFiles(Map<String, Object> param) { public Map<String, Object> parsingFiles(Map<String, Object> param) {
try { try {
@ -46,6 +60,7 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
if (StringUtils.isBlank(imageId)) { if (StringUtils.isBlank(imageId)) {
throw new CustomizeRunTimeException("文件获取失败,请确认文件是否上传"); throw new CustomizeRunTimeException("文件获取失败,请确认文件是否上传");
} }
baseBean.writeLog("imageId==" + imageId);
Map<String, Object> returnMap = new HashMap<>(); Map<String, Object> returnMap = new HashMap<>();
// 根据文件id获取文件流 // 根据文件id获取文件流
ImageFileManager manager = new ImageFileManager(); ImageFileManager manager = new ImageFileManager();
@ -53,17 +68,21 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
manager.getImageFileName(); manager.getImageFileName();
InputStream inputStream = manager.getInputStream(); InputStream inputStream = manager.getInputStream();
Path tempZipFile = Files.createTempFile("temp", ".zip"); Path fixedDir = Paths.get(GCONST.getRootPath() + "filesystem" + File.separatorChar + "downloadBatchTemp");
Files.createDirectories(fixedDir);
Path tempZipFile = Files.createTempFile(fixedDir, "offline_temp_", ".zip");
baseBean.writeLog("tempZipFile==" + tempZipFile.toString());
Files.copy(inputStream, tempZipFile, StandardCopyOption.REPLACE_EXISTING); Files.copy(inputStream, tempZipFile, StandardCopyOption.REPLACE_EXISTING);
String password = "zizhi102!";
//解压文件处理压缩包 //解压文件处理压缩包
unzipWithPassword(tempZipFile, Paths.get("output"), password); baseBean.writeLog("开始解压文件,处理压缩包");
unzipWithPassword(tempZipFile, Paths.get("output"), UNZIP_PWD);
baseBean.writeLog("压缩包处理完成");
return returnMap; return returnMap;
} catch (Exception e) { } catch (Exception e) {
throw new CustomizeRunTimeException("文件解析失败", e); throw new CustomizeRunTimeException(e.getMessage(), e);
} }
} }
@ -82,41 +101,47 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
} }
// 遍历并解压所有文件 // 遍历并解压所有文件
zipFile.extractAll(outputDir.toString()); zipFile.extractAll(outputDir.toString());
baseBean.writeLog("已解压所有文件");
// 遍历 ZIP 内文件可选 // 遍历 ZIP 内文件可选
List<FileHeader> fileHeaders = zipFile.getFileHeaders(); List<FileHeader> fileHeaders = zipFile.getFileHeaders();
// 获取压缩包解析后的根目录 imageFileMap = new HashMap<>();
Optional<String> commonRoot = fileHeaders.stream()
.map(FileHeader::getFileName)
.filter(path -> !path.trim().isEmpty())
.map(path -> path.split("/")[0])
.distinct()
.reduce((a, b) -> a.equals(b) ? a : null);
String rootPath = commonRoot.orElse("");
// TODO 测试 后续删除
Map<String, FileHeader> fileHeaderMap = new HashMap<>();
for (FileHeader header : fileHeaders) { for (FileHeader header : fileHeaders) {
if (header.isDirectory()) { if (header.isDirectory()) {
continue; continue;
} }
System.out.println("文件: " + header.getFileName()); String fullPath = header.getFileName();
fileHeaderMap.put(header.getFileName(), header); int lastSlashIndex = fullPath.lastIndexOf('/');
String fileName = (lastSlashIndex != -1)
? fullPath.substring(lastSlashIndex + 1)
: fullPath;
baseBean.writeLog("文件名称: " + fileName);
// 上传文件
int imageFileId = generateImageFileId(zipFile, header, fileName);
imageFileMap.put(fileName, imageFileId);
} }
baseBean.writeLog("fileHeaders.size==" + fileHeaders.size());
baseBean.writeLog("imageFileMap.size==" + imageFileMap.size());
baseBean.writeLog("imageFileMap==" + JSON.toJSONString(imageFileMap));
// 获取数据文件用于后续数据解析 // 获取数据文件用于后续数据解析
String jsonFileName = StringUtils.isBlank(rootPath) ? "(database)data.json" : rootPath + "/(database)data.json"; Integer dataJsonImageId = imageFileMap.get("(database)data.json");
FileHeader jsonFileHeader = zipFile.getFileHeader(jsonFileName);
if (jsonFileHeader != null) { if (dataJsonImageId != null && dataJsonImageId > 0) {
// 离线端方式 // 离线端方式
offline(zipFile, jsonFileHeader); JsonNode rootNode = parseJsonContent(dataJsonImageId);
offline(rootNode, imageFileMap);
} }
// TODO 兼容其他方式 // TODO 兼容其他方式
} catch (IOException e) { } catch (Exception e) {
if (e.getMessage().contains("Wrong password")) { if (e.getMessage().contains("Wrong password")) {
System.err.println("密码错误"); System.err.println("密码错误");
} else { } else {
@ -134,17 +159,24 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
/** /**
* 离线解析方式 * 离线解析方式
* *
* @param zipFile * @param rootNode
* @param jsonFileHeader * @param imageFileMap
* @throws JsonProcessingException * @throws JsonProcessingException
*/ */
private void offline(ZipFile zipFile, FileHeader jsonFileHeader) throws JsonProcessingException { private void offline(JsonNode rootNode, Map<String, Integer> imageFileMap) throws Exception {
// 解析JSON文件
String jsonContent = parseJsonContent(zipFile, jsonFileHeader);
ObjectMapper mapper = new ObjectMapper();
JsonNode rootNode = mapper.readTree(jsonContent);
List<DataConfig> dataConfigList = getDataConfig("0"); List<DataConfig> dataConfigList = getDataConfig("0");
// 处理文件数据
List<ApplicationResource> applicationResourceList = getApplicationResourceList(rootNode);
// key是fid 集合是该同一个fid下的文件ID信息
applicationResourceMap = applicationResourceList.stream().collect(Collectors.groupingBy(ApplicationResource::getFid));
baseBean.writeLog("applicationResourceMap==" + JSON.toJSONString(applicationResourceMap));
List<ResourceInfo> resourceInfoList = getResourceInfoList(rootNode);
// key是fid 集合是该同一个fid下的文件ID信息
resourceInfoMap = resourceInfoList.stream().collect(Collectors.groupingBy(ResourceInfo::getVirtualPath, Collectors.toMap(ResourceInfo::getId, item -> item)));
baseBean.writeLog("resourceInfoMap==" + JSON.toJSONString(resourceInfoMap));
if (CollectionUtils.isNotEmpty(dataConfigList)) { if (CollectionUtils.isNotEmpty(dataConfigList)) {
// 遍历配置读取配置文件并插入数据 // 遍历配置读取配置文件并插入数据
for (DataConfig dataConfig : dataConfigList) { for (DataConfig dataConfig : dataConfigList) {
@ -183,6 +215,7 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
continue; continue;
} }
dealDetailData(rootNode, billId, childDataConfigList); dealDetailData(rootNode, billId, childDataConfigList);
// TODO 更新文件信息
} }
} else { } else {
int billId = insertMainTable(rootNode, mainTableName, fieldDetailList); int billId = insertMainTable(rootNode, mainTableName, fieldDetailList);
@ -190,6 +223,8 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
continue; continue;
} }
dealDetailData(rootNode, billId, childDataConfigList); dealDetailData(rootNode, billId, childDataConfigList);
// TODO 更新文件信息
dealFileList(billId, fileList, mainTableName, false);
} }
} }
@ -205,7 +240,7 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
* @param mainId * @param mainId
* @param childDataConfigList * @param childDataConfigList
*/ */
private void dealDetailData(JsonNode rootNode, int mainId, List<DataConfig> childDataConfigList) { private void dealDetailData(JsonNode rootNode, int mainId, List<DataConfig> childDataConfigList) throws Exception {
if (CollectionUtils.isEmpty(childDataConfigList)) { if (CollectionUtils.isEmpty(childDataConfigList)) {
return; return;
} }
@ -213,27 +248,35 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
String detailTableName = childDataConfig.getDetailTableName(); String detailTableName = childDataConfig.getDetailTableName();
// 获取字段对照关系数据 // 获取字段对照关系数据
List<DataConfigDetail> fieldList = childDataConfig.getDetailList(); List<DataConfigDetail> fieldList = childDataConfig.getDetailList();
String rootPath = childDataConfig.getRootPath(); List<FileConfig> fileList = childDataConfig.getFileList();
if (StringUtils.isNotBlank(rootPath)) { // 明细表文件配置不为空的情况下只处理文件不做其他数据插入处理
if (rootPath.contains("[*]")) { if (CollectionUtils.isNotEmpty(fileList)) {
rootPath = rootPath.replace("[*]", ""); baseBean.writeLog("开始解析文件,写入明细数据");
JsonNode jsonNode = rootNode.at(rootPath); dealFileList(mainId, fileList, detailTableName, true);
if (null == jsonNode) {
throw new CustomizeRunTimeException("数据解析失败,未找到对应字段:[" + rootPath + "]"); } else {
} String rootPath = childDataConfig.getRootPath();
if (!jsonNode.isArray()) { if (StringUtils.isNotBlank(rootPath)) {
throw new CustomizeRunTimeException("数据解析失败,未找到对应字段集合:[" + rootPath + "]"); if (rootPath.contains("[*]")) {
} rootPath = rootPath.replace("[*]", "");
for (JsonNode node : jsonNode) { JsonNode jsonNode = rootNode.at(rootPath);
insertDetailTable(node, detailTableName, mainId, fieldList); if (null == jsonNode) {
throw new CustomizeRunTimeException("数据解析失败,未找到对应字段:[" + rootPath + "]");
}
if (!jsonNode.isArray()) {
throw new CustomizeRunTimeException("数据解析失败,未找到对应字段集合:[" + rootPath + "]");
}
for (JsonNode node : jsonNode) {
insertDetailTable(node, detailTableName, mainId, fieldList);
}
} else {
JsonNode jsonNode = rootNode.at(rootPath);
insertDetailTable(jsonNode, detailTableName, mainId, fieldList);
} }
} else { } else {
JsonNode jsonNode = rootNode.at(rootPath); insertDetailTable(rootNode, detailTableName, mainId, fieldList);
insertDetailTable(jsonNode, detailTableName, mainId, fieldList);
} }
} else {
insertDetailTable(rootNode, detailTableName, mainId, fieldList);
} }
} }
} }
@ -278,7 +321,7 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
// TODO ModeUtil.insertData(insertMap, mainTableName); // TODO ModeUtil.insertData(insertMap, mainTableName);
// 数据权限重构,返回数据ID // 数据权限重构,返回数据ID
// TODO return ModeUtil.refreshRight(uuid, mainTableName, formModeId, user.getUID()); // TODO return ModeUtil.refreshRight(uuid, mainTableName, formModeId, user.getUID());
System.out.println("insertMainTable: " + JSON.toJSONString(insertMap)); baseBean.writeLog("insertMainTable: " + JSON.toJSONString(insertMap));
return 1; return 1;
} }
@ -314,12 +357,79 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
return; return;
} }
insertMap.put("mainId", mainId); insertMap.put("mainId", mainId);
System.out.println("insertDetailTable: " + JSON.toJSONString(insertMap)); baseBean.writeLog("insertDetailTable: " + JSON.toJSONString(insertMap));
// 插入数据 // 插入数据
// TODO ModeUtil.insertData(insertMap, detailTableName); // TODO ModeUtil.insertData(insertMap, detailTableName);
} }
/**
* 处理文件数据
*
* @param mainId
* @param fileConfigList
* @param tableName
* @param isDetail
* @throws Exception
*/
private void dealFileList(int mainId, List<FileConfig> fileConfigList, String tableName, boolean isDetail) throws Exception {
Map<String, Object> dataMap = new IgnoreCaseHashMap<>();
for (FileConfig fileConfig : fileConfigList) {
String fieldName = fileConfig.getFieldName();
// 是否更正文件
String isFilled = fileConfig.getIsFilled();
// 文件标识ID
String fileId = fileConfig.getFileId();
List<ApplicationResource> applicationResources = applicationResourceMap.get(fileId);
if (CollectionUtils.isEmpty(applicationResources)) {
baseBean.writeLog("根据fid未获取到数据fileId==" + fileId);
continue;
}
Map<String, ResourceInfo> fileResourceMap = resourceInfoMap.get(isFilled);
if (null == fileResourceMap || fileResourceMap.size() == 0) {
baseBean.writeLog("根据文件类型未获取到数据isFilled==" + isFilled);
continue;
}
List<String> fileRidList = applicationResources.stream().map(ApplicationResource::getRid).collect(Collectors.toList());
List<Integer> docIds = new ArrayList<>();
for (String rid : fileRidList) {
ResourceInfo resourceInfo = fileResourceMap.get(rid);
if (resourceInfo == null) {
baseBean.writeLog("根据文件rid未获取到数据rid==" + rid + ",isFilled==" + isFilled);
continue;
}
String fileName = resourceInfo.getFileName();
Integer imageFileId = imageFileMap.get(fileName);
// 生成文档ID
int docId = ModeUtil.createDocId(UPLOAD_CATALOGUE, imageFileId, user);
docIds.add(docId);
}
dataMap.put(fieldName, StringUtils.join(docIds, ","));
}
if (dataMap.size() == 0) {
baseBean.writeLog("dataMap集合为空");
return;
}
baseBean.writeLog("文件插入集合dataMap==" + JSON.toJSONString(dataMap));
// 根据主表明细表区分数据处理方式
if (isDetail) {
dataMap.put("mainid", mainId);
//TODO ModeUtil.insertData(dataMap,tableName);
} else {
dataMap.put("id", mainId);
// 根据ID更新主表数据
// TODO ModeUtil.updateDataById(dataMap, tableName);
}
}
/** /**
* 获取数据配置 * 获取数据配置
* *
@ -415,24 +525,85 @@ public class QualificationApplicationServiceImpl extends Service implements Qual
rs.executeQuery("select * from " + FILE_DETAIL_TABLE_NAME + " where mainId = ?", mainId); rs.executeQuery("select * from " + FILE_DETAIL_TABLE_NAME + " where mainId = ?", mainId);
while (rs.next()) { while (rs.next()) {
// TODO 表名字段名待确定 // TODO 表名字段名待确定
fileList.add(FileConfig.builder().filedName(rs.getString("zdm")).fileId(rs.getString("wjbs")).isFilled(rs.getString("bzwj")).build()); fileList.add(FileConfig.builder().fieldName(rs.getString("zdm")).fileId(rs.getString("wjbs")).isFilled(rs.getString("bzwj")).build());
} }
return fileList; return fileList;
} }
/**
* 获取JSON文件中applicationResourceList数组
*
* @param rootNode
* @return
*/
private List<ApplicationResource> getApplicationResourceList(JsonNode rootNode) {
List<ApplicationResource> applicationResourceList = new ArrayList<>();
JsonNode applicationResourceListNode = rootNode.at("/applicationResourceList");
if (applicationResourceListNode != null && applicationResourceListNode.isArray()) {
for (JsonNode jsonNode : applicationResourceListNode) {
String id = jsonNode.at("/id").asText();
String aid = jsonNode.at("/aid").asText();
String fid = jsonNode.at("/fid").asText();
String rid = jsonNode.at("/rid").asText();
String createdTime = jsonNode.at("/createdTime").asText();
String isDelete = jsonNode.at("/isDelete").asText();
applicationResourceList.add(ApplicationResource.builder().id(id).aid(aid).fid(fid).rid(rid).createdTime(createdTime).isDelete(isDelete).build());
}
}
return applicationResourceList;
}
/**
* 获取JSON文件中resourceInfoList数组
*
* @param rootNode
* @return
*/
private List<ResourceInfo> getResourceInfoList(JsonNode rootNode) {
List<ResourceInfo> resourceInfoList = new ArrayList<>();
JsonNode resourceInfoListNode = rootNode.at("/resourceInfoList");
if (resourceInfoListNode != null && resourceInfoListNode.isArray()) {
for (JsonNode jsonNode : resourceInfoListNode) {
String id = jsonNode.at("/id").asText();
String fileName = jsonNode.at("/fileName").asText();
String filePath = jsonNode.at("/filePath").asText();
String fileSuffix = jsonNode.at("/fileSuffix").asText();
String virtualPath = jsonNode.at("/virtualPath").asText();
String createdTime = jsonNode.at("/createdTime").asText();
String updatedTime = jsonNode.at("/updatedTime").asText();
String isDelete = jsonNode.at("/isDelete").asText();
resourceInfoList.add(ResourceInfo.builder().id(id).fileName(fileName).filePath(filePath).fileSuffix(fileSuffix).virtualPath(virtualPath).createdTime(createdTime).updatedTime(updatedTime).isDelete(isDelete).build());
}
}
return resourceInfoList;
}
/** /**
* 获取JSON文件内容 * 获取JSON文件内容
* *
* @param imageFieldId
* @return
* @throws IOException
*/
private static JsonNode parseJsonContent(Integer imageFieldId) throws IOException {
ImageFileManager manager = new ImageFileManager();
manager.getImageFileInfoById(imageFieldId);
InputStream inputStream = manager.getInputStream();
ObjectMapper mapper = new ObjectMapper();
return mapper.readTree(inputStream);
}
/**
* 上传文件 返回imageFileId
*
* @param zipFile * @param zipFile
* @param header * @param header
* @return * @return
*/ */
private static String parseJsonContent(ZipFile zipFile, FileHeader header) { private int generateImageFileId(ZipFile zipFile, FileHeader header, String fileName) {
ObjectMapper mapper = new ObjectMapper();
try (InputStream is = zipFile.getInputStream(header)) { try (InputStream is = zipFile.getInputStream(header)) {
JsonNode rootNode = mapper.readTree(is); return ModeUtil.generateImageFileId(is, fileName);
return rootNode.toPrettyString();
} catch (Exception e) { } catch (Exception e) {
throw new CustomizeRunTimeException(e); throw new CustomizeRunTimeException(e);
} }

View File

@ -321,4 +321,6 @@ public class ModeUtil {
} }
return formModeId; return formModeId;
} }
} }