|
@@ -364,7 +364,7 @@ public class IotOpeationFillController {
|
|
|
/**
|
|
/**
|
|
|
* 处理累计逻辑
|
|
* 处理累计逻辑
|
|
|
*/
|
|
*/
|
|
|
- private void processSummationLogic(List<IotOpeationFillSaveReqVO> allFillData) {
|
|
|
|
|
|
|
+ /*private void processSummationLogic(List<IotOpeationFillSaveReqVO> allFillData) {
|
|
|
// 按modelId分组,便于查找
|
|
// 按modelId分组,便于查找
|
|
|
Map<Long, List<IotOpeationFillSaveReqVO>> modelIdMap = allFillData.stream()
|
|
Map<Long, List<IotOpeationFillSaveReqVO>> modelIdMap = allFillData.stream()
|
|
|
.filter(fill -> fill.getModelId() != null)
|
|
.filter(fill -> fill.getModelId() != null)
|
|
@@ -415,8 +415,80 @@ public class IotOpeationFillController {
|
|
|
//log.warn("DefaultValue转换失败: {}", fill.getDefaultValue());
|
|
//log.warn("DefaultValue转换失败: {}", fill.getDefaultValue());
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
+ }*/
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 处理累计逻辑(优化后:批量查询历史数据)
|
|
|
|
|
+ */
|
|
|
|
|
+ private void processSummationLogic(List<IotOpeationFillSaveReqVO> allFillData) {
|
|
|
|
|
+ // 按modelId分组(不变)
|
|
|
|
|
+ Map<Long, List<IotOpeationFillSaveReqVO>> modelIdMap = allFillData.stream()
|
|
|
|
|
+ .filter(fill -> fill.getModelId() != null)
|
|
|
|
|
+ .collect(Collectors.groupingBy(IotOpeationFillSaveReqVO::getModelId));
|
|
|
|
|
+
|
|
|
|
|
+ // 筛选需要累计的数据(不变)
|
|
|
|
|
+ List<IotOpeationFillSaveReqVO> sumDataList = allFillData.stream()
|
|
|
|
|
+ .filter(fill -> 1 == fill.getIsSum()
|
|
|
|
|
+ && StringUtils.isEmpty(fill.getDefaultValue())
|
|
|
|
|
+ && StringUtils.isEmpty(fill.getDefaultValue().trim()))
|
|
|
|
|
+ .collect(Collectors.toList());
|
|
|
|
|
+
|
|
|
|
|
+ if (CollectionUtils.isEmpty(sumDataList)) {
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 1. 批量构建查询条件(避免循环查询)
|
|
|
|
|
+ List<IotDeviceRunLogDO> queryLogs = sumDataList.stream()
|
|
|
|
|
+ .map(fill -> {
|
|
|
|
|
+ IotDeviceRunLogDO queryLog = new IotDeviceRunLogDO();
|
|
|
|
|
+ queryLog.setDeviceId(fill.getDeviceId());
|
|
|
|
|
+ queryLog.setPointName(fill.getPointName());
|
|
|
|
|
+ queryLog.setCreateTime(LocalDateTime.of(fill.getCreateTime(), LocalTime.MIDNIGHT));
|
|
|
|
|
+ return queryLog;
|
|
|
|
|
+ })
|
|
|
|
|
+ .collect(Collectors.toList());
|
|
|
|
|
+
|
|
|
|
|
+ // 2. 批量查询历史最大数据(1次数据库交互)
|
|
|
|
|
+ List<IotDeviceRunLogDO> maxFillDataList = iotOpeationFillService.batchQueryMaxReportData(queryLogs);
|
|
|
|
|
+ Map<String, BigDecimal> maxDataMap = maxFillDataList.stream()
|
|
|
|
|
+ .filter(data -> data.getTotalRunTime() != null)
|
|
|
|
|
+ .collect(Collectors.toMap(
|
|
|
|
|
+ data -> data.getDeviceId() + "_" + data.getPointName(), // 设备+测点唯一标识
|
|
|
|
|
+ IotDeviceRunLogDO::getTotalRunTime
|
|
|
|
|
+ ));
|
|
|
|
|
+
|
|
|
|
|
+ // 3. 并行处理累计计算(CPU密集型,并行提速)
|
|
|
|
|
+ sumDataList.parallelStream().forEach(fill -> {
|
|
|
|
|
+ try {
|
|
|
|
|
+ Long refModelId = Long.parseLong(fill.getDefaultValue());
|
|
|
|
|
+ List<IotOpeationFillSaveReqVO> targetFills = modelIdMap.get(refModelId);
|
|
|
|
|
+ if (CollectionUtils.isEmpty(targetFills)) {
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ BigDecimal total = BigDecimal.ZERO;
|
|
|
|
|
+ for (IotOpeationFillSaveReqVO targetFill : targetFills) {
|
|
|
|
|
+ BigDecimal currentValue = new BigDecimal(targetFill.getFillContent());
|
|
|
|
|
+ if (fill.getSumId() == 1) {
|
|
|
|
|
+ // 累加:从缓存获取历史最大值
|
|
|
|
|
+ String key = fill.getDeviceId() + "_" + fill.getPointName();
|
|
|
|
|
+ BigDecimal maxHistory = maxDataMap.getOrDefault(key, BigDecimal.ZERO);
|
|
|
|
|
+ total = maxHistory.add(currentValue);
|
|
|
|
|
+ } else if (fill.getSumId() == 0) {
|
|
|
|
|
+ // 直接赋值
|
|
|
|
|
+ total = currentValue;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ fill.setTotalRunTime(total);
|
|
|
|
|
+ } catch (NumberFormatException e) {
|
|
|
|
|
+ //log.warn("DefaultValue转换失败: {}", fill.getDefaultValue());
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
/**
|
|
/**
|
|
|
* 处理数据累加
|
|
* 处理数据累加
|
|
|
*/
|
|
*/
|
|
@@ -523,7 +595,7 @@ public class IotOpeationFillController {
|
|
|
/**
|
|
/**
|
|
|
* 批量保存日志
|
|
* 批量保存日志
|
|
|
*/
|
|
*/
|
|
|
- private void batchSaveLogs(List<IotDeviceRunLogDO> logDOList) {
|
|
|
|
|
|
|
+ /*private void batchSaveLogs(List<IotDeviceRunLogDO> logDOList) {
|
|
|
for (IotDeviceRunLogDO log : logDOList) {
|
|
for (IotDeviceRunLogDO log : logDOList) {
|
|
|
IotDeviceRunLogDO existingData = iotOpeationFillService.reportData(log);
|
|
IotDeviceRunLogDO existingData = iotOpeationFillService.reportData(log);
|
|
|
if (existingData == null) {
|
|
if (existingData == null) {
|
|
@@ -536,8 +608,66 @@ public class IotOpeationFillController {
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
+ }*/
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 批量保存日志(优化后:批量查询+批量插入+批量更新)
|
|
|
|
|
+ */
|
|
|
|
|
+ private void batchSaveLogs(List<IotDeviceRunLogDO> logDOList) {
|
|
|
|
|
+ if (CollectionUtils.isEmpty(logDOList)) {
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 1. 批量查询已存在的数据(用复合索引:deviceId+pointName+createTime)
|
|
|
|
|
+ List<IotDeviceRunLogDO> existingLogs = iotOpeationFillService.batchQueryExistingLogs(logDOList);
|
|
|
|
|
+ Map<String, IotDeviceRunLogDO> existingLogMap = existingLogs.stream()
|
|
|
|
|
+ .collect(Collectors.toMap(
|
|
|
|
|
+ log -> buildLogUniqueKey(log), // 构建唯一标识:deviceId_pointName_createTime
|
|
|
|
|
+ log -> log,
|
|
|
|
|
+ (v1, v2) -> v1 // 避免重复key(理论上不会有)
|
|
|
|
|
+ ));
|
|
|
|
|
+
|
|
|
|
|
+ // 2. 拆分:待插入列表 + 待更新列表
|
|
|
|
|
+ List<IotDeviceRunLogDO> insertList = new ArrayList<>();
|
|
|
|
|
+ List<IotDeviceRunLogDO> updateList = new ArrayList<>();
|
|
|
|
|
+ List<IotDeviceRunLogDO> updateSumList = new ArrayList<>();
|
|
|
|
|
+
|
|
|
|
|
+ for (IotDeviceRunLogDO log : logDOList) {
|
|
|
|
|
+ String key = buildLogUniqueKey(log);
|
|
|
|
|
+ if (existingLogMap.containsKey(key)) {
|
|
|
|
|
+ // 已存在:区分普通更新和累计更新
|
|
|
|
|
+ if (log.getIsSum() == 0) {
|
|
|
|
|
+ updateList.add(log);
|
|
|
|
|
+ } else {
|
|
|
|
|
+ updateSumList.add(log);
|
|
|
|
|
+ }
|
|
|
|
|
+ } else {
|
|
|
|
|
+ // 不存在:插入
|
|
|
|
|
+ insertList.add(log);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 3. 批量执行(MyBatis批量操作)
|
|
|
|
|
+ if (!insertList.isEmpty()) {
|
|
|
|
|
+ iotOpeationFillService.batchInsertLogs(insertList); // 批量插入
|
|
|
|
|
+ }
|
|
|
|
|
+ if (!updateList.isEmpty()) {
|
|
|
|
|
+ iotOpeationFillService.batchUpdateLogs(updateList); // 批量更新普通日志
|
|
|
|
|
+ }
|
|
|
|
|
+ if (!updateSumList.isEmpty()) {
|
|
|
|
|
+ iotOpeationFillService.batchUpdateSumLogs(updateSumList); // 批量更新累计日志
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 构建日志唯一标识(用于快速查找已存在数据)
|
|
|
|
|
+ */
|
|
|
|
|
+ private String buildLogUniqueKey(IotDeviceRunLogDO log) {
|
|
|
|
|
+ return log.getDeviceId() + "_" + log.getPointName() + "_" + log.getCreateTime().toLocalDate();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ //*******************批量保存到这********************
|
|
|
|
|
+
|
|
|
/**
|
|
/**
|
|
|
* 获取部门ID集合
|
|
* 获取部门ID集合
|
|
|
*/
|
|
*/
|
|
@@ -558,7 +688,7 @@ public class IotOpeationFillController {
|
|
|
/**
|
|
/**
|
|
|
* 生成日报
|
|
* 生成日报
|
|
|
*/
|
|
*/
|
|
|
- private void generateDailyReports(List<IotDeviceRunLogDO> logDOList,
|
|
|
|
|
|
|
+ /*private void generateDailyReports(List<IotDeviceRunLogDO> logDOList,
|
|
|
Map<String, Set<Long>> deptMap,
|
|
Map<String, Set<Long>> deptMap,
|
|
|
LocalDate createDate,
|
|
LocalDate createDate,
|
|
|
Integer userId) {
|
|
Integer userId) {
|
|
@@ -586,12 +716,55 @@ public class IotOpeationFillController {
|
|
|
processDepartmentReport(deviceLogs, fillStatus, deptMap, createDate);
|
|
processDepartmentReport(deviceLogs, fillStatus, deptMap, createDate);
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
+ }*/
|
|
|
|
|
+ private void generateDailyReports(List<IotDeviceRunLogDO> logDOList,
|
|
|
|
|
+ Map<String, Set<Long>> deptMap,
|
|
|
|
|
+ LocalDate createDate,
|
|
|
|
|
+ Integer userId) {
|
|
|
|
|
+ if (CollectionUtils.isEmpty(logDOList)) {
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 1. 批量查询所有测点描述(1次数据库交互,避免循环查询)
|
|
|
|
|
+ Set<String> pointNameSet = logDOList.stream()
|
|
|
|
|
+ .map(IotDeviceRunLogDO::getPointName)
|
|
|
|
|
+ .filter(Objects::nonNull)
|
|
|
|
|
+ .collect(Collectors.toSet());
|
|
|
|
|
+ List<IotDeviceRunLogDO> descList = iotOpeationFillService.batchGetDescByPointNames(pointNameSet);
|
|
|
|
|
+ Map<String, IotDeviceRunLogDO> descMap = descList.stream()
|
|
|
|
|
+ .collect(Collectors.toMap(
|
|
|
|
|
+ IotDeviceRunLogDO::getPointName,
|
|
|
|
|
+ desc -> desc,
|
|
|
|
|
+ (v1, v2) -> v1
|
|
|
|
|
+ ));
|
|
|
|
|
+
|
|
|
|
|
+ // 2. 按设备分组(不变)
|
|
|
|
|
+ Map<Long, List<IotDeviceRunLogDO>> deviceLogsMap = logDOList.stream()
|
|
|
|
|
+ .collect(Collectors.groupingBy(IotDeviceRunLogDO::getDeviceId));
|
|
|
|
|
+
|
|
|
|
|
+ // 3. 并行处理每个设备的日报(IO密集型,并行提速)
|
|
|
|
|
+ deviceLogsMap.entrySet().parallelStream().forEach(entry -> {
|
|
|
|
|
+ List<IotDeviceRunLogDO> deviceLogs = entry.getValue();
|
|
|
|
|
+ IotDeviceRunLogDO sampleLog = deviceLogs.get(0);
|
|
|
|
|
+
|
|
|
|
|
+ // 查询上报状态(单条查询无法避免,但并行执行)
|
|
|
|
|
+ IotOpeationFillDO reportQuery = new IotOpeationFillDO();
|
|
|
|
|
+ reportQuery.setDeviceId(sampleLog.getDeviceId());
|
|
|
|
|
+ reportQuery.setCreateTime(sampleLog.getCreateTime());
|
|
|
|
|
+ IotOpeationFillDO fillStatus = iotOpeationFillService.isReport(reportQuery);
|
|
|
|
|
+
|
|
|
|
|
+ if (fillStatus != null && fillStatus.getIsReport() != null && fillStatus.getIsReport() == 1) {
|
|
|
|
|
+ fillStatus.setUserId(userId);
|
|
|
|
|
+ // 处理部门日报
|
|
|
|
|
+ processDepartmentReport(deviceLogs, fillStatus, deptMap, createDate, descMap);
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
|
* 处理部门日报生成
|
|
* 处理部门日报生成
|
|
|
*/
|
|
*/
|
|
|
- private void processDepartmentReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
|
|
+ /*private void processDepartmentReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
IotOpeationFillDO fillStatus,
|
|
IotOpeationFillDO fillStatus,
|
|
|
Map<String, Set<Long>> deptMap,
|
|
Map<String, Set<Long>> deptMap,
|
|
|
LocalDate createDate) {
|
|
LocalDate createDate) {
|
|
@@ -603,12 +776,30 @@ public class IotOpeationFillController {
|
|
|
} else if (ryIdList.contains(fillStatus.getDeptId())) {
|
|
} else if (ryIdList.contains(fillStatus.getDeptId())) {
|
|
|
generateRyDailyReport(deviceLogs, fillStatus, createDate);
|
|
generateRyDailyReport(deviceLogs, fillStatus, createDate);
|
|
|
}
|
|
}
|
|
|
|
|
+ }*/
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 处理部门日报生成(新增descMap缓存)
|
|
|
|
|
+ */
|
|
|
|
|
+ private void processDepartmentReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
+ IotOpeationFillDO fillStatus,
|
|
|
|
|
+ Map<String, Set<Long>> deptMap,
|
|
|
|
|
+ LocalDate createDate,
|
|
|
|
|
+ Map<String, IotDeviceRunLogDO> descMap) {
|
|
|
|
|
+ Set<Long> rhIdList = deptMap.get("RH");
|
|
|
|
|
+ Set<Long> ryIdList = deptMap.get("RY");
|
|
|
|
|
+
|
|
|
|
|
+ if (rhIdList.contains(fillStatus.getDeptId())) {
|
|
|
|
|
+ generateRhDailyReport(deviceLogs, fillStatus, createDate, descMap);
|
|
|
|
|
+ } else if (ryIdList.contains(fillStatus.getDeptId())) {
|
|
|
|
|
+ generateRyDailyReport(deviceLogs, fillStatus, createDate, descMap);
|
|
|
|
|
+ }
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
|
* 生成RH日报
|
|
* 生成RH日报
|
|
|
*/
|
|
*/
|
|
|
- private void generateRhDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
|
|
+ /*private void generateRhDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
IotOpeationFillDO fillStatus,
|
|
IotOpeationFillDO fillStatus,
|
|
|
LocalDate createDate) {
|
|
LocalDate createDate) {
|
|
|
IotRhDailyReportSaveReqVO saveReqVO = new IotRhDailyReportSaveReqVO();
|
|
IotRhDailyReportSaveReqVO saveReqVO = new IotRhDailyReportSaveReqVO();
|
|
@@ -630,13 +821,38 @@ public class IotOpeationFillController {
|
|
|
finalReport.setFillOrderCreateTime(createDate.atStartOfDay());
|
|
finalReport.setFillOrderCreateTime(createDate.atStartOfDay());
|
|
|
finalReport.setCreator(String.valueOf(fillStatus.getUserId()));
|
|
finalReport.setCreator(String.valueOf(fillStatus.getUserId()));
|
|
|
|
|
|
|
|
|
|
+ iotRhDailyReportService.createIotRhDailyReport(finalReport);
|
|
|
|
|
+ }*/
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 生成RH日报(使用缓存的descMap)
|
|
|
|
|
+ */
|
|
|
|
|
+ private void generateRhDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
+ IotOpeationFillDO fillStatus,
|
|
|
|
|
+ LocalDate createDate,
|
|
|
|
|
+ Map<String, IotDeviceRunLogDO> descMap) {
|
|
|
|
|
+ IotRhDailyReportSaveReqVO saveReqVO = new IotRhDailyReportSaveReqVO();
|
|
|
|
|
+ Map<String, Object> reportData = BeanUtil.beanToMap(saveReqVO);
|
|
|
|
|
+
|
|
|
|
|
+ for (IotDeviceRunLogDO log : deviceLogs) {
|
|
|
|
|
+ IotDeviceRunLogDO descDO = descMap.get(log.getPointName()); // 从缓存获取,无数据库交互
|
|
|
|
|
+ if (descDO != null && reportData.containsKey(descDO.getPointName())) {
|
|
|
|
|
+ reportData.put(descDO.getPointName(), log.getFillContent());
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 后续赋值和保存逻辑不变(建议日报也做批量保存,若存在多条设备)
|
|
|
|
|
+ IotRhDailyReportSaveReqVO finalReport = BeanUtil.mapToBean(reportData, IotRhDailyReportSaveReqVO.class, false);
|
|
|
|
|
+ finalReport.setDeptId(fillStatus.getDeptId());
|
|
|
|
|
+ finalReport.setFillOrderCreateTime(createDate.atStartOfDay());
|
|
|
|
|
+ finalReport.setCreator(String.valueOf(fillStatus.getUserId()));
|
|
|
iotRhDailyReportService.createIotRhDailyReport(finalReport);
|
|
iotRhDailyReportService.createIotRhDailyReport(finalReport);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
|
* 生成RY日报
|
|
* 生成RY日报
|
|
|
*/
|
|
*/
|
|
|
- private void generateRyDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
|
|
+ /*private void generateRyDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
IotOpeationFillDO fillStatus,
|
|
IotOpeationFillDO fillStatus,
|
|
|
LocalDate createDate) {
|
|
LocalDate createDate) {
|
|
|
IotRyDailyReportSaveReqVO saveReqVO = new IotRyDailyReportSaveReqVO();
|
|
IotRyDailyReportSaveReqVO saveReqVO = new IotRyDailyReportSaveReqVO();
|
|
@@ -663,8 +879,30 @@ public class IotOpeationFillController {
|
|
|
finalReport.setProjectClassification("2");
|
|
finalReport.setProjectClassification("2");
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ iotRyDailyReportService.createIotRyDailyReport(finalReport);
|
|
|
|
|
+ }*/
|
|
|
|
|
+ private void generateRyDailyReport(List<IotDeviceRunLogDO> deviceLogs,
|
|
|
|
|
+ IotOpeationFillDO fillStatus,
|
|
|
|
|
+ LocalDate createDate,
|
|
|
|
|
+ Map<String, IotDeviceRunLogDO> descMap) {
|
|
|
|
|
+ IotRyDailyReportSaveReqVO saveReqVO = new IotRyDailyReportSaveReqVO();
|
|
|
|
|
+ Map<String, Object> reportData = BeanUtil.beanToMap(saveReqVO);
|
|
|
|
|
+
|
|
|
|
|
+ for (IotDeviceRunLogDO log : deviceLogs) {
|
|
|
|
|
+ IotDeviceRunLogDO descDO = descMap.get(log.getPointName()); // 从缓存获取,无数据库交互
|
|
|
|
|
+ if (descDO != null && reportData.containsKey(descDO.getPointName())) {
|
|
|
|
|
+ reportData.put(descDO.getPointName(), log.getFillContent());
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 后续赋值和保存逻辑不变(建议日报也做批量保存,若存在多条设备)
|
|
|
|
|
+ IotRyDailyReportSaveReqVO finalReport = BeanUtil.mapToBean(reportData, IotRyDailyReportSaveReqVO.class, false);
|
|
|
|
|
+ finalReport.setDeptId(fillStatus.getDeptId());
|
|
|
|
|
+ finalReport.setFillOrderCreateTime(createDate.atStartOfDay());
|
|
|
|
|
+ finalReport.setCreator(String.valueOf(fillStatus.getUserId()));
|
|
|
iotRyDailyReportService.createIotRyDailyReport(finalReport);
|
|
iotRyDailyReportService.createIotRyDailyReport(finalReport);
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
//************************************************8
|
|
//************************************************8
|
|
|
|
|
|
|
|
@PostMapping("/upOperationOrder")
|
|
@PostMapping("/upOperationOrder")
|