|
@@ -3,43 +3,36 @@ package com.css.simulation.resource.server.app.service;
|
|
|
import api.common.pojo.common.ResponseBodyVO;
|
|
|
import api.common.pojo.constants.DictConstants;
|
|
|
import api.common.pojo.enums.SceneEvaluationEnum;
|
|
|
-import api.common.pojo.param.MinioParameter;
|
|
|
import api.common.pojo.param.scene.*;
|
|
|
import api.common.pojo.po.scene.SceneComplexityPO;
|
|
|
import api.common.pojo.po.scene.SceneEvaluationOperatePO;
|
|
|
import api.common.pojo.po.scene.SceneEvaluationRulePO;
|
|
|
import api.common.pojo.po.scene.SceneRiskPO;
|
|
|
-import api.common.util.*;
|
|
|
+import api.common.util.LogUtil;
|
|
|
+import api.common.util.StringUtil;
|
|
|
+import api.common.util.TimeUtil;
|
|
|
import com.alibaba.druid.util.StringUtils;
|
|
|
import com.css.simulation.resource.server.infra.db.mysql.mapper.SceneComplexityMapper;
|
|
|
import com.css.simulation.resource.server.infra.db.mysql.mapper.SceneEvaluationRuleMapper;
|
|
|
import com.css.simulation.resource.server.infra.db.mysql.mapper.ScenePackageMapper;
|
|
|
import com.css.simulation.resource.server.infra.db.mysql.mapper.SceneRiskMapper;
|
|
|
import com.css.simulation.resource.server.infra.feign.service.FileDownService;
|
|
|
+import com.css.simulation.resource.server.infra.runnable.SceneEvaluationComputeRunnable;
|
|
|
+import com.css.simulation.resource.server.infra.threadpool.ThreadPool;
|
|
|
import com.css.simulation.resource.server.infra.util.AuthUtil;
|
|
|
-import com.fasterxml.jackson.databind.JsonNode;
|
|
|
-import com.fasterxml.jackson.databind.ObjectMapper;
|
|
|
-import feign.Response;
|
|
|
import lombok.SneakyThrows;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
-import org.springframework.beans.BeanUtils;
|
|
|
import org.springframework.beans.factory.annotation.Value;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
import org.springframework.web.multipart.MultipartFile;
|
|
|
|
|
|
import javax.annotation.Resource;
|
|
|
-import java.io.*;
|
|
|
-import java.nio.charset.StandardCharsets;
|
|
|
-import java.nio.file.Files;
|
|
|
-import java.nio.file.Path;
|
|
|
-import java.nio.file.Paths;
|
|
|
-import java.nio.file.attribute.PosixFilePermission;
|
|
|
-import java.util.*;
|
|
|
+import java.util.Date;
|
|
|
+import java.util.List;
|
|
|
+import java.util.Map;
|
|
|
import java.util.function.Function;
|
|
|
import java.util.stream.Collectors;
|
|
|
|
|
|
-import static api.common.pojo.enums.SceneEvaluationEnum.matchLevelEnumByLevel;
|
|
|
-
|
|
|
@Slf4j
|
|
|
@Service
|
|
|
public class SceneEvaluationRuleService {
|
|
@@ -120,6 +113,61 @@ public class SceneEvaluationRuleService {
|
|
|
return new ResponseBodyVO<>(ResponseBodyVO.Response.SUCCESS);
|
|
|
}
|
|
|
|
|
|
+
|
|
|
+ @SneakyThrows
|
|
|
+ public ResponseBodyVO<String> uploadPyScriptAndSaveRuleByPath(SceneEvaluationRulePO sceneEvaluationRulePO) {
|
|
|
+
|
|
|
+ boolean hasRuleId = StringUtil.isEmpty(sceneEvaluationRulePO.getRuleId());
|
|
|
+
|
|
|
+ // 检查是否存在同名场景评价规则
|
|
|
+ int repeatPyScriptAndSaveRuleCount = querySceneEvaluationRuleOnly(sceneEvaluationRulePO.getRuleName(),
|
|
|
+ hasRuleId ? null : sceneEvaluationRulePO.getRuleId());
|
|
|
+ if (repeatPyScriptAndSaveRuleCount > 0) {
|
|
|
+ return new ResponseBodyVO<>(ResponseBodyVO.Response.CLIENT_FAILURE, "场景规则 " + sceneEvaluationRulePO.getRuleName() + " 已存在,请重新命名。");
|
|
|
+ }
|
|
|
+ // 新建或者是编辑时重新上传文件
|
|
|
+ if ((hasRuleId) || sceneEvaluationRulePO.getUploadNewFile()) {
|
|
|
+ String roleCode = AuthUtil.getCurrentUserRoleCode();
|
|
|
+ if (!DictConstants.ROLE_CODE_ADMIN.equals(roleCode) && !DictConstants.ROLE_CODE_SYSADMIN.equals(roleCode)) {
|
|
|
+ return new ResponseBodyVO<>(ResponseBodyVO.Response.CLIENT_FAILURE, "非管理员禁止上传文件");
|
|
|
+ }
|
|
|
+ // 检查文件内容是否合规
|
|
|
+// String pyStr = new String(file.getBytes(), StandardCharsets.UTF_8);
|
|
|
+// //1 校验 python 语法错误
|
|
|
+// String pylint = PythonUtil.pylint(pyStr, PythonUtil.C, PythonUtil.R, PythonUtil.W, PythonUtil.E0401, PythonUtil.E0601);
|
|
|
+// if (!pylint.contains(PythonUtil.PASS)) {
|
|
|
+// return new ResponseBodyVO<>(ResponseBodyVO.Response.CLIENT_FAILURE, "代码格式错误,请检查。");
|
|
|
+// }
|
|
|
+// // 获取文件原本的名字
|
|
|
+// String originName = file.getOriginalFilename();
|
|
|
+// if (null == originName) {
|
|
|
+// return new ResponseBodyVO<>(ResponseBodyVO.Response.CLIENT_FAILURE, "文件名为空,请检查!");
|
|
|
+// }
|
|
|
+// Integer nowTime = TimeUtil.getRq(new Date(), 0);
|
|
|
+// String randomCode = StringUtil.getRandomCode();
|
|
|
+// String fileName = "/" + DictConstants.SCENE_EVALUATION_RULE_PY_FILE + "/" + nowTime + "/" + randomCode + "/" + originName;
|
|
|
+// ResponseBodyVO<String> response = fileDownService.upload(file, fileName);
|
|
|
+// if (response.isStatus()) {
|
|
|
+// sceneEvaluationRulePO.setScriptName(originName);
|
|
|
+// sceneEvaluationRulePO.setScriptPath(fileName);
|
|
|
+// } else {
|
|
|
+// return new ResponseBodyVO<>(ResponseBodyVO.Response.CLIENT_FAILURE, "上传失败!");
|
|
|
+// }
|
|
|
+// }
|
|
|
+//
|
|
|
+// // 判断 ruleId 是否为空
|
|
|
+// if (StringUtil.isEmpty(sceneEvaluationRulePO.getRuleId())) {
|
|
|
+// // 创建
|
|
|
+// saveSceneEvaluationRule(sceneEvaluationRulePO);
|
|
|
+// } else {
|
|
|
+// // 修改
|
|
|
+// updateSceneEvaluationRule(sceneEvaluationRulePO);
|
|
|
+// }
|
|
|
+ }
|
|
|
+ return new ResponseBodyVO<>(ResponseBodyVO.Response.SUCCESS);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
@SneakyThrows
|
|
|
public void deleteSceneEvaluationRule(SceneEvaluationRulePO params) {
|
|
|
// todo 如果是复杂度脚本需要校验是否有自然/交通等模板有引用
|
|
@@ -217,238 +265,8 @@ public class SceneEvaluationRuleService {
|
|
|
}
|
|
|
|
|
|
|
|
|
- /**
|
|
|
- * 场景上传计算复杂度,计算复杂度需要用到 osc 和 odr 路径,计算危险度用 evaluationPath
|
|
|
- *
|
|
|
- * @param param
|
|
|
- */
|
|
|
- public boolean computeSceneReference(SceneImportParam param, List<SceneEvaluationComputeParam> sceneEvaluationComputeParams) {
|
|
|
- String ruleId = param.getSceneEvaluationRuleId();
|
|
|
- // 获取场景评价规则
|
|
|
- SceneEvaluationRulePO sceneEvaluationRulePO = sceneEvaluationRuleMapper.querySceneEvaluationPyById(ruleId);
|
|
|
- if (sceneEvaluationRulePO == null) {
|
|
|
- log.error(ruleId + " 的场景评价规则已删除");
|
|
|
- return false;
|
|
|
- }
|
|
|
- // 1 判断有没有用户目录,没有则复制
|
|
|
- String evaluationDirectoryOfUser = linuxTempPath + "scene/evaluation/" + sceneEvaluationComputeParams.get(0).getTaskId() + "/";
|
|
|
- String scriptsPath = evaluationDirectoryOfUser + "scripts";
|
|
|
- if (!new File(evaluationDirectoryOfUser).exists()) {
|
|
|
- // 1 将场景评价规则脚本保存到 script 目录
|
|
|
- FileUtil.createDirectory(scriptsPath);
|
|
|
-// final ArrayList<String> scriptFilePath = CollectionUtil.createArrayList(
|
|
|
-// "/data_preprocessing.py",
|
|
|
-// "/elevation.py",
|
|
|
-// "/scenario_evaluation_utils52.py"
|
|
|
-// );
|
|
|
-// for (String pyFilePath : scriptFilePath) {
|
|
|
-// try {
|
|
|
-// downloadDependFile(sceneEvaluationScript + pyFilePath, scriptsPath + pyFilePath);
|
|
|
-// } catch (IOException e) {
|
|
|
-// log.error("下载 py 依赖文件失败: " + sceneEvaluationScript + pyFilePath, e);
|
|
|
-// return false;
|
|
|
-// }
|
|
|
-// }
|
|
|
- }
|
|
|
-
|
|
|
- // 下载场景评价脚本到脚本目录
|
|
|
- if (sceneEvaluationRulePO.getScriptPath() == null) {
|
|
|
- return false;
|
|
|
- }
|
|
|
- String pyMainPath = scriptsPath + "/" + sceneEvaluationRulePO.getRuleId();
|
|
|
- if (!new File(pyMainPath).exists()) {
|
|
|
- try {
|
|
|
- downloadDependFile(sceneEvaluationRulePO.getScriptPath(), pyMainPath);
|
|
|
- Path path = Paths.get(pyMainPath);
|
|
|
- Set<PosixFilePermission> permissions = new HashSet<>();
|
|
|
- permissions.add(PosixFilePermission.OWNER_READ);
|
|
|
- permissions.add(PosixFilePermission.OWNER_WRITE);
|
|
|
- permissions.add(PosixFilePermission.OWNER_EXECUTE);
|
|
|
- permissions.add(PosixFilePermission.GROUP_READ);
|
|
|
- permissions.add(PosixFilePermission.GROUP_WRITE);
|
|
|
- permissions.add(PosixFilePermission.GROUP_EXECUTE);
|
|
|
- permissions.add(PosixFilePermission.OTHERS_READ);
|
|
|
- permissions.add(PosixFilePermission.OTHERS_WRITE);
|
|
|
- permissions.add(PosixFilePermission.OTHERS_EXECUTE);
|
|
|
- Files.setPosixFilePermissions(path, permissions);
|
|
|
- } catch (IOException e) {
|
|
|
- log.error("下载执行文件失败: " + sceneEvaluationRulePO.getScriptPath(), e);
|
|
|
- return false;
|
|
|
- }
|
|
|
- }
|
|
|
- String scenePathFather = evaluationDirectoryOfUser + "scene/";
|
|
|
- for (SceneEvaluationComputeParam sceneEvaluationComputeParam : sceneEvaluationComputeParams) {
|
|
|
- // 创建场景路径
|
|
|
- String scenePath = scenePathFather + sceneEvaluationComputeParam.getSceneId();
|
|
|
- if (!new File(scenePath).exists()) {
|
|
|
- FileUtil.createDirectory(scenePath);
|
|
|
- } else {
|
|
|
- // 一个场景只计算一次
|
|
|
- return false;
|
|
|
- }
|
|
|
- try {
|
|
|
- if (StringUtils.equals(sceneEvaluationComputeParam.getComputeType(), DictConstants.COMPLEXITY)) {
|
|
|
- if (StringUtil.isEmpty(sceneEvaluationComputeParam.getSceneXODRPath())
|
|
|
- || StringUtil.isEmpty(sceneEvaluationComputeParam.getSceneXOSCPath())) {
|
|
|
- continue;
|
|
|
- }
|
|
|
- // 计算复杂度,根据场景 id 获取场景信息,下载 osc odr
|
|
|
- String scenarioOsc = sceneEvaluationComputeParam.getSceneXOSCPath();
|
|
|
- String[] splitXosc = scenarioOsc.split("/");
|
|
|
- String xoscName = splitXosc[splitXosc.length - 1];
|
|
|
- downloadDependFile(sceneEvaluationComputeParam.getSceneXOSCPath(), scenePath + "/" + xoscName);
|
|
|
-
|
|
|
- String scenarioOdr = sceneEvaluationComputeParam.getSceneXODRPath();
|
|
|
- String[] splitXodr = scenarioOdr.split("/");
|
|
|
- String xodrName = splitXodr[splitXodr.length - 1];
|
|
|
- downloadDependFile(sceneEvaluationComputeParam.getSceneXODRPath(), scenePath + "/" + xodrName);
|
|
|
- } else if (StringUtils.equals(sceneEvaluationComputeParam.getComputeType(), DictConstants.RISK)) {
|
|
|
- if (StringUtil.isEmpty(sceneEvaluationComputeParam.getEvaluationPath())) {
|
|
|
- continue;
|
|
|
- }
|
|
|
- // 计算危险度 从 minio path 下载 csv (ego 和 sensors)
|
|
|
- downloadDependFile(sceneEvaluationComputeParam.getEvaluationPath() + "/Ego.csv", scenePath + "/Ego.csv");
|
|
|
- downloadDependFile(sceneEvaluationComputeParam.getEvaluationPath() + "/evaluation.csv", scenePath + "/evaluation.csv");
|
|
|
- } else {
|
|
|
- return false;
|
|
|
- }
|
|
|
- } catch (IOException e) {
|
|
|
- log.error("文件下载失败", e);
|
|
|
- FileUtil.deleteFolder(scenePath); // 删除临时文件
|
|
|
- }
|
|
|
- }
|
|
|
- String sceneEvaluationCommand;
|
|
|
- if (StringUtils.equals(sceneEvaluationComputeParams.get(0).getComputeType(), DictConstants.COMPLEXITY)) {
|
|
|
- sceneEvaluationCommand = pyMainPath + " " + scenePathFather + " complexity";
|
|
|
- } else {
|
|
|
- sceneEvaluationCommand = pyMainPath + " " + scenePathFather + " criticality";
|
|
|
- }
|
|
|
- String sceneEvaluationResult;
|
|
|
- log.info("开始执行场景评价命令:" + sceneEvaluationCommand);
|
|
|
- Runtime r = Runtime.getRuntime();
|
|
|
- Process p;
|
|
|
- try {
|
|
|
- p = r.exec(sceneEvaluationCommand);
|
|
|
- } catch (IOException e) {
|
|
|
- log.error("执行场景评价脚本失败,脚本命令为: " + sceneEvaluationCommand, e);
|
|
|
- return false;
|
|
|
- }
|
|
|
-
|
|
|
- StringBuilder sb = new StringBuilder();
|
|
|
- try {
|
|
|
- BufferedReader br = new BufferedReader(new InputStreamReader(p.getInputStream()));
|
|
|
- String inline;
|
|
|
- while ((inline = br.readLine()) != null) {
|
|
|
- sb.append(inline).append("\n");
|
|
|
- }
|
|
|
- br.close();
|
|
|
- } catch (IOException e) {
|
|
|
- log.error("获取场景评价脚本返回内容失败", e);
|
|
|
- return false;
|
|
|
- }
|
|
|
- sceneEvaluationResult = sb.toString();
|
|
|
- log.info("场景评价结束,结果为:" + sceneEvaluationResult);
|
|
|
- for (SceneEvaluationComputeParam sceneEvaluationComputeParam : sceneEvaluationComputeParams) {
|
|
|
- // 读文件
|
|
|
- StringBuilder result = new StringBuilder();
|
|
|
- try {
|
|
|
- FileInputStream fileInputStream = new FileInputStream(scenePathFather + sceneEvaluationComputeParam.getSceneId() + "/scenario_evaluation.json");
|
|
|
- BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(fileInputStream));
|
|
|
-
|
|
|
- String line;
|
|
|
- while ((line = bufferedReader.readLine()) != null) {
|
|
|
- result.append(line).append("\n");
|
|
|
- }
|
|
|
- bufferedReader.close();
|
|
|
- } catch (IOException e) {
|
|
|
- log.error("读取场景评价结果失败", e);
|
|
|
- continue;
|
|
|
- }
|
|
|
- String resultStr = result.toString();
|
|
|
- String replace = StringUtil.replace(resultStr, "'", "\"");
|
|
|
- JsonNode rootNode;
|
|
|
- try {
|
|
|
- ObjectMapper mapper = new ObjectMapper();
|
|
|
- //JSON ----> JsonNode
|
|
|
- rootNode = mapper.readTree(replace);
|
|
|
-
|
|
|
- if (StringUtils.equals(sceneEvaluationComputeParam.getComputeType(), DictConstants.COMPLEXITY)) {
|
|
|
- String complexity = rootNode.path("复杂度").asText();
|
|
|
- String complexityLevel = rootNode.path("复杂度等级").asText();
|
|
|
- SceneComplexityPO sceneComplexityPO = new SceneComplexityPO();
|
|
|
- sceneComplexityPO.setSceneId(sceneEvaluationComputeParam.getSceneId());
|
|
|
- sceneComplexityPO.setComplexityId(StringUtil.getRandomUUID());
|
|
|
- sceneComplexityPO.setSceneType(sceneEvaluationComputeParam.getSceneType());
|
|
|
- sceneComplexityPO.setRuleId(ruleId);
|
|
|
- sceneComplexityPO.setTaskId(sceneEvaluationComputeParam.getTaskId());
|
|
|
- sceneComplexityPO.setComplexity(complexity);
|
|
|
- sceneComplexityPO.setComplexityLevel(matchLevelEnumByLevel(complexityLevel));
|
|
|
- sceneComplexityPO.setIsDeleted(DictConstants.IS_NOT_DELETED);
|
|
|
- sceneComplexityPO.setCreateUserId(AuthUtil.getCurrentUserId());
|
|
|
- sceneComplexityPO.setCreateTime(TimeUtil.getNowForMysql());
|
|
|
- sceneComplexityMapper.saveSceneComplexity(sceneComplexityPO);
|
|
|
- if (CollectionUtil.isNotEmpty(sceneEvaluationComputeParam.getCopySceneId())) {
|
|
|
- copySceneComplexityResult(sceneEvaluationComputeParam.getTaskId(), sceneEvaluationComputeParam.getSceneId(), sceneEvaluationComputeParam.getCopySceneId());
|
|
|
- }
|
|
|
- } else {
|
|
|
- String risk = rootNode.path("危险度").asText();
|
|
|
- String riskLevel = rootNode.path("危险度等级").asText();
|
|
|
- SceneRiskPO sceneRiskPO = new SceneRiskPO();
|
|
|
- sceneRiskPO.setSceneId(sceneEvaluationComputeParam.getSceneId());
|
|
|
- sceneRiskPO.setRuleId(StringUtil.getRandomUUID());
|
|
|
- sceneRiskPO.setSceneType(sceneEvaluationComputeParam.getSceneType());
|
|
|
- sceneRiskPO.setRuleId(ruleId);
|
|
|
- sceneRiskPO.setTaskId(sceneEvaluationComputeParam.getTaskId());
|
|
|
- sceneRiskPO.setRisk(risk);
|
|
|
- sceneRiskPO.setRiskLevel(matchLevelEnumByLevel(riskLevel));
|
|
|
- sceneRiskPO.setIsDeleted(DictConstants.IS_NOT_DELETED);
|
|
|
- sceneRiskPO.setCreateUserId(AuthUtil.getCurrentUserId());
|
|
|
- sceneRiskPO.setCreateTime(TimeUtil.getNowForMysql());
|
|
|
- sceneRiskMapper.saveSceneRisk(sceneRiskPO);
|
|
|
- }
|
|
|
- } catch (Exception e) {
|
|
|
- log.error("场景" + sceneEvaluationComputeParam.getSceneId() + " 的场景评价失败:", e);
|
|
|
- }
|
|
|
- }
|
|
|
- // 删除临时文件
|
|
|
-// FileUtil.deleteFolder(linuxTempPath + "scene/evaluation/" + sceneEvaluationComputeParams.get(0).getTaskId()); // 删除临时文件
|
|
|
- return true;
|
|
|
- }
|
|
|
-
|
|
|
- private void downloadDependFile(String minioPath, String localPath) throws IOException {
|
|
|
- Response download = fileDownService.download(MinioParameter.builder().objectName(minioPath).build());
|
|
|
- Response.Body body = download.body();
|
|
|
- InputStream inputStream;
|
|
|
- inputStream = body.asInputStream();
|
|
|
- File file = new File(localPath);
|
|
|
- OutputStream outputStream = Files.newOutputStream(file.toPath());
|
|
|
- byte[] buffer = new byte[1024];
|
|
|
- int bytesRead;
|
|
|
- while ((bytesRead = inputStream.read(buffer)) != -1) {
|
|
|
- outputStream.write(buffer, 0, bytesRead);
|
|
|
- }
|
|
|
- inputStream.close();
|
|
|
- outputStream.close();
|
|
|
- download.close();
|
|
|
- }
|
|
|
-
|
|
|
- public void copySceneComplexityResult(String taskId, String tempSceneId, List<String> copySceneIds) {
|
|
|
- List<SceneComplexityPO> sceneComplexityPOS = sceneComplexityMapper.selectSceneComplexityEvaluation(taskId, tempSceneId);
|
|
|
- List<SceneComplexityPO> saveList = new ArrayList<>();
|
|
|
- if (CollectionUtil.isNotEmpty(sceneComplexityPOS)) {
|
|
|
- for (SceneComplexityPO sceneComplexityPO : sceneComplexityPOS) {
|
|
|
- for (String copySceneId : copySceneIds) {
|
|
|
- SceneComplexityPO tempComplexityPO = new SceneComplexityPO();
|
|
|
- BeanUtils.copyProperties(sceneComplexityPO, tempComplexityPO);
|
|
|
- tempComplexityPO.setSceneId(copySceneId);
|
|
|
- tempComplexityPO.setComplexityId(StringUtil.getRandomUUID());
|
|
|
- saveList.add(tempComplexityPO);
|
|
|
- }
|
|
|
- }
|
|
|
- if (CollectionUtil.isNotEmpty(saveList)) {
|
|
|
- sceneComplexityMapper.saveSceneComplexityS(saveList);
|
|
|
- }
|
|
|
- }
|
|
|
+ public void computeSceneReference(SceneImportParam param, List<SceneEvaluationComputeParam> sceneEvaluationComputeParams) {
|
|
|
+ ThreadPool.sceneEvaluationComputePool.execute(new SceneEvaluationComputeRunnable(param, sceneEvaluationComputeParams, linuxTempPath));
|
|
|
}
|
|
|
|
|
|
public boolean checkSelectReferenceComplexity(String sceneId, SceneEvaluationForListParam sceneEvaluationForListParam, Map<String, SceneComplexityPO> complexityPOMap) {
|