fix: 流量数据删除
This commit is contained in:
parent
2e7b6d6650
commit
b59aaa58d6
@ -1,9 +1,11 @@
|
|||||||
package com.yfd.platform.qgc_eng.eq.controller;
|
package com.yfd.platform.qgc_eng.eq.controller;
|
||||||
|
|
||||||
|
import com.yfd.platform.annotation.Log;
|
||||||
import com.yfd.platform.common.DataSourceLoadOptionsBase;
|
import com.yfd.platform.common.DataSourceLoadOptionsBase;
|
||||||
import com.yfd.platform.common.DataSourceRequest;
|
import com.yfd.platform.common.DataSourceRequest;
|
||||||
import com.yfd.platform.common.DataSourceResult;
|
import com.yfd.platform.common.DataSourceResult;
|
||||||
import com.yfd.platform.config.ResponseResult;
|
import com.yfd.platform.config.ResponseResult;
|
||||||
|
import com.yfd.platform.qgc_base.entity.vo.BatchDeleteAo;
|
||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqBaseMsstbprptVo;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqBaseMsstbprptVo;
|
||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqBaseVmsstbprptVo;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqBaseVmsstbprptVo;
|
||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqDrtpDataVo;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.EngEqDrtpDataVo;
|
||||||
@ -193,4 +195,12 @@ public class EngEqDataController {
|
|||||||
public ResponseResult getMsEngKendoListCust(@RequestBody DataSourceRequest dataSourceRequest) {
|
public ResponseResult getMsEngKendoListCust(@RequestBody DataSourceRequest dataSourceRequest) {
|
||||||
return ResponseResult.successData(engEqDataService.getMsEngKendoList(dataSourceRequest));
|
return ResponseResult.successData(engEqDataService.getMsEngKendoList(dataSourceRequest));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Log(module = "生态流量监测数据管理", value = "删除生态流量小时/日/月数据")
|
||||||
|
@PostMapping("/data/removeKendoByIds")
|
||||||
|
@Operation(summary = "删除生态流量小时/日/月数据")
|
||||||
|
public ResponseResult removeKendoByIds(@RequestBody BatchDeleteAo batchDeleteAo) {
|
||||||
|
engEqDataService.removeKendoByIds(batchDeleteAo);
|
||||||
|
return ResponseResult.success();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2,6 +2,7 @@ package com.yfd.platform.qgc_eng.eq.service;
|
|||||||
|
|
||||||
import com.yfd.platform.common.DataSourceRequest;
|
import com.yfd.platform.common.DataSourceRequest;
|
||||||
import com.yfd.platform.common.DataSourceResult;
|
import com.yfd.platform.common.DataSourceResult;
|
||||||
|
import com.yfd.platform.qgc_base.entity.vo.BatchDeleteAo;
|
||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.*;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.*;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@ -76,4 +77,12 @@ public interface EngEqDataService {
|
|||||||
* <p>对应旧系统 EngEqController.getKendoListCust</p>
|
* <p>对应旧系统 EngEqController.getKendoListCust</p>
|
||||||
*/
|
*/
|
||||||
DataSourceResult<EngEqDataVo> getMsEngKendoList(DataSourceRequest dataSourceRequest);
|
DataSourceResult<EngEqDataVo> getMsEngKendoList(DataSourceRequest dataSourceRequest);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 批量删除生态流量小时/日/月数据
|
||||||
|
* <p>删除小时数据后会按受影响站点重新聚合日表(SD_QECDAY_S)和月表(SD_QECDRTP_S)</p>
|
||||||
|
*
|
||||||
|
* @param batchDeleteAo dataType: TIME=小时 DATE=日 MON=月;dataList: 删除数据列表
|
||||||
|
*/
|
||||||
|
boolean removeKendoByIds(BatchDeleteAo batchDeleteAo);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,6 +1,7 @@
|
|||||||
package com.yfd.platform.qgc_eng.eq.service.impl;
|
package com.yfd.platform.qgc_eng.eq.service.impl;
|
||||||
|
|
||||||
import cn.hutool.core.collection.CollUtil;
|
import cn.hutool.core.collection.CollUtil;
|
||||||
|
import cn.hutool.core.date.DateUtil;
|
||||||
import cn.hutool.core.util.StrUtil;
|
import cn.hutool.core.util.StrUtil;
|
||||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||||
import com.yfd.platform.common.DataSourceLoadOptionsBase;
|
import com.yfd.platform.common.DataSourceLoadOptionsBase;
|
||||||
@ -37,15 +38,26 @@ import com.yfd.platform.qgc_eng.eq.entity.vo.WbsbVo;
|
|||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.StBaseInfo;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.StBaseInfo;
|
||||||
import com.yfd.platform.qgc_eng.eq.entity.vo.StcdInfoVo;
|
import com.yfd.platform.qgc_eng.eq.entity.vo.StcdInfoVo;
|
||||||
import com.yfd.platform.qgc_eng.eq.service.EngEqDataService;
|
import com.yfd.platform.qgc_eng.eq.service.EngEqDataService;
|
||||||
|
import com.yfd.platform.qgc_base.domain.MsOperationLog;
|
||||||
|
import com.yfd.platform.qgc_base.domain.MsOperationLogDetail;
|
||||||
|
import com.yfd.platform.qgc_base.entity.vo.BatchDeleteAo;
|
||||||
|
import com.yfd.platform.qgc_base.entity.vo.DataParam;
|
||||||
|
import com.yfd.platform.qgc_base.mapper.MsOperationLogDetailMapper;
|
||||||
|
import com.yfd.platform.qgc_base.mapper.MsOperationLogMapper;
|
||||||
import com.yfd.platform.qgc_env.wq.entity.vo.MsWarnRuleDetailBVo;
|
import com.yfd.platform.qgc_env.wq.entity.vo.MsWarnRuleDetailBVo;
|
||||||
import com.yfd.platform.qgc_env.wt.utils.SiteAvoidanceUtils;
|
import com.yfd.platform.qgc_env.wt.utils.SiteAvoidanceUtils;
|
||||||
import com.yfd.platform.utils.QgcQueryWrapperUtil;
|
import com.yfd.platform.utils.QgcQueryWrapperUtil;
|
||||||
|
import com.yfd.platform.utils.SecurityUtils;
|
||||||
import jakarta.annotation.Resource;
|
import jakarta.annotation.Resource;
|
||||||
|
import org.springframework.jdbc.core.JdbcTemplate;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Calendar;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
import java.util.LinkedHashMap;
|
import java.util.LinkedHashMap;
|
||||||
import java.util.LinkedHashSet;
|
import java.util.LinkedHashSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@ -67,6 +79,39 @@ public class EngEqDataServiceImpl implements EngEqDataService {
|
|||||||
@Resource
|
@Resource
|
||||||
private MicroservicDynamicSQLMapper microservicDynamicSQLMapper;
|
private MicroservicDynamicSQLMapper microservicDynamicSQLMapper;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private JdbcTemplate jdbcTemplate;
|
||||||
|
|
||||||
|
private static final String QEC_HOUR_TABLE_NAME = "SD_QEC_R";
|
||||||
|
private static final String QEC_DAY_TABLE_NAME = "SD_QECDAY_S";
|
||||||
|
private static final String QEC_DRTP_TABLE_NAME = "SD_QECDRTP_S";
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private MsOperationLogMapper msOperationLogMapper;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private MsOperationLogDetailMapper msOperationLogDetailMapper;
|
||||||
|
|
||||||
|
private static final LinkedHashMap<String, String> QEC_FIELD_MEANING_MAP = new LinkedHashMap<>();
|
||||||
|
|
||||||
|
static {
|
||||||
|
QEC_FIELD_MEANING_MAP.put("QEC", "生态流量");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("WATERFLOW", "AI识别生态流量值");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("TPQEC", "生态流量泄放方式");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("SFDB", "生态流量是否达标");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("MWR_SFDB", "生态流量是否达标(水利部)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("AVQ_SFDB", "生态流量是否达标(多年平均)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("QEC_LIMIT", "生态流量限值(环保部)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("MWR_LIMIT", "生态流量限值(水利部)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("AVQ_LIMIT", "生态流量限值(多年平均)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("QEC_C", "生态流量限值系数(环保部)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("MWR_C", "生态流量限值系数(水利部)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("AVQ_C", "生态流量系数(多年平均)");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("QEC_RULE_DID", "环保部生态流量告警规则详情ID");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("QEC_MWRRULE_DID", "水利部生态流量告警规则详情ID");
|
||||||
|
QEC_FIELD_MEANING_MAP.put("SHOW_FLAG", "数据显示类型");
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public DataSourceResult getKendoListCust(DataSourceRequest dataSourceRequest) {
|
public DataSourceResult getKendoListCust(DataSourceRequest dataSourceRequest) {
|
||||||
DataSourceLoadOptionsBase loadOptions = dataSourceRequest == null ? null : dataSourceRequest.toDevRequest();
|
DataSourceLoadOptionsBase loadOptions = dataSourceRequest == null ? null : dataSourceRequest.toDevRequest();
|
||||||
@ -6671,4 +6716,529 @@ public class EngEqDataServiceImpl implements EngEqDataService {
|
|||||||
return "tm".equalsIgnoreCase(field);
|
return "tm".equalsIgnoreCase(field);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
@Transactional(rollbackFor = Exception.class)
|
||||||
|
public boolean removeKendoByIds(BatchDeleteAo batchDeleteAo) {
|
||||||
|
List<DataParam> dataList = batchDeleteAo == null ? null : batchDeleteAo.getDataList();
|
||||||
|
if (CollUtil.isEmpty(dataList)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
String dataType = StrUtil.blankToDefault(batchDeleteAo.getDataType(), "").toUpperCase();
|
||||||
|
String source = batchDeleteAo == null ? null : batchDeleteAo.getSource();
|
||||||
|
int batchSize = 500;
|
||||||
|
for (int i = 0; i < dataList.size(); i += batchSize) {
|
||||||
|
List<DataParam> subList = dataList.subList(i, Math.min(i + batchSize, dataList.size()));
|
||||||
|
if ("MON".equals(dataType)) {
|
||||||
|
List<Map<String, Object>> beforeRows = queryQecMonthRows(subList);
|
||||||
|
softDeleteQecDrtpData(subList);
|
||||||
|
recordQecDeleteLog(beforeRows, QEC_DRTP_TABLE_NAME, "删除生态流量月数据", source);
|
||||||
|
}
|
||||||
|
if ("DATE".equals(dataType)) {
|
||||||
|
List<Map<String, Object>> beforeRows = queryQecDayRows(subList);
|
||||||
|
softDeleteQecDayData(subList);
|
||||||
|
recordQecDeleteLog(beforeRows, QEC_DAY_TABLE_NAME, "删除生态流量日数据", source);
|
||||||
|
}
|
||||||
|
if ("TIME".equals(dataType)) {
|
||||||
|
List<Map<String, Object>> beforeRows = queryQecHourRows(subList);
|
||||||
|
deleteQecHourData(subList);
|
||||||
|
recordQecDeleteLog(beforeRows, QEC_HOUR_TABLE_NAME, "删除生态流量小时数据", source);
|
||||||
|
|
||||||
|
Map<String, String[]> dateRangeMap = new HashMap<>();
|
||||||
|
Map<String, String[]> monthRangeMap = new HashMap<>();
|
||||||
|
for (DataParam param : subList) {
|
||||||
|
String stcd = param == null ? null : param.getId();
|
||||||
|
String tm = param == null ? null : param.getTm();
|
||||||
|
if (StrUtil.isBlank(stcd) || StrUtil.isBlank(tm) || tm.length() < 10) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
String dateStr = tm.substring(0, 10);
|
||||||
|
dateRangeMap.compute(stcd, (key, range) -> {
|
||||||
|
if (range == null) {
|
||||||
|
return new String[]{dateStr, dateStr};
|
||||||
|
}
|
||||||
|
if (dateStr.compareTo(range[0]) < 0) {
|
||||||
|
range[0] = dateStr;
|
||||||
|
}
|
||||||
|
if (dateStr.compareTo(range[1]) > 0) {
|
||||||
|
range[1] = dateStr;
|
||||||
|
}
|
||||||
|
return range;
|
||||||
|
});
|
||||||
|
|
||||||
|
String[] ym = tm.substring(0, 7).split("-");
|
||||||
|
if (ym.length == 2) {
|
||||||
|
Integer year = Integer.parseInt(ym[0]);
|
||||||
|
Integer month = Integer.parseInt(ym[1]);
|
||||||
|
String monthStart = year + "-" + String.format("%02d", month) + "-01";
|
||||||
|
String monthEnd = getMonthEndDate(year, month);
|
||||||
|
monthRangeMap.putIfAbsent(stcd + "_" + year + "_" + month,
|
||||||
|
new String[]{stcd, monthStart, monthEnd});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (Map.Entry<String, String[]> entry : dateRangeMap.entrySet()) {
|
||||||
|
statisticsQecDayDataFromHour(entry.getKey(), entry.getValue()[0], entry.getValue()[1]);
|
||||||
|
}
|
||||||
|
Set<String> processedMonths = new HashSet<>();
|
||||||
|
for (String[] values : monthRangeMap.values()) {
|
||||||
|
String monthKey = values[0] + "_" + values[1];
|
||||||
|
if (processedMonths.add(monthKey)) {
|
||||||
|
statisticsQecMonthDataFromDay(values[0], values[1], values[2]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void softDeleteQecDrtpData(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("MERGE INTO SD_QECDRTP_S target USING (");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" UNION ALL ");
|
||||||
|
}
|
||||||
|
sql.append("SELECT ? AS STCD, ? AS DRTP, ? AS YEAR, ? AS MONTH FROM DUAL");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getDrtp());
|
||||||
|
params.add(item == null ? null : item.getYear());
|
||||||
|
params.add(item == null ? null : item.getMonth());
|
||||||
|
}
|
||||||
|
sql.append(") source ON (target.STCD = source.STCD AND target.DRTP = source.DRTP ")
|
||||||
|
.append("AND target.YEAR = source.YEAR AND target.MONTH = source.MONTH) ")
|
||||||
|
.append("WHEN MATCHED THEN UPDATE SET target.IS_DELETED = 1, target.DELETE_TIME = SYSDATE");
|
||||||
|
jdbcTemplate.update(sql.toString(), params.toArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void softDeleteQecDayData(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("MERGE INTO SD_QECDAY_S target USING (");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" UNION ALL ");
|
||||||
|
}
|
||||||
|
sql.append("SELECT ? AS STCD, TO_DATE(?, 'YYYY-MM-DD HH24:MI:SS') AS DT FROM DUAL");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getDt());
|
||||||
|
}
|
||||||
|
sql.append(") source ON (target.STCD = source.STCD AND target.DT = source.DT) ")
|
||||||
|
.append("WHEN MATCHED THEN UPDATE SET target.IS_DELETED = 1, target.DELETE_TIME = SYSDATE");
|
||||||
|
jdbcTemplate.update(sql.toString(), params.toArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void deleteQecHourData(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("DELETE FROM SD_QEC_R WHERE ");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" OR ");
|
||||||
|
}
|
||||||
|
sql.append("(STCD = ? AND TM = TO_DATE(?, 'YYYY-MM-DD HH24:MI:SS'))");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getTm());
|
||||||
|
}
|
||||||
|
jdbcTemplate.update(sql.toString(), params.toArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void appendHourRowConditions(StringBuilder sql, List<Object> params, List<DataParam> dataParamList) {
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" OR ");
|
||||||
|
}
|
||||||
|
sql.append("(STCD = ? AND TM = TO_DATE(?, 'YYYY-MM-DD HH24:MI:SS'))");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getTm());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String buildQecHourLogSelectColumns() {
|
||||||
|
return "ID,STCD, TO_CHAR(TM, 'YYYY-MM-DD HH24:MI:SS') AS TM, " +
|
||||||
|
"QEC, WATERFLOW, TPQEC, SFDB, MWR_SFDB, AVQ_SFDB, " +
|
||||||
|
"QEC_LIMIT, MWR_LIMIT, AVQ_LIMIT, QEC_C, MWR_C, AVQ_C, " +
|
||||||
|
"QEC_RULE_DID, QEC_MWRRULE_DID, SHOW_FLAG";
|
||||||
|
}
|
||||||
|
|
||||||
|
private String buildQecDayLogSelectColumns() {
|
||||||
|
return "ID,STCD, TO_CHAR(DT, 'YYYY-MM-DD HH24:MI:SS') AS DT, " +
|
||||||
|
"QEC, WATERFLOW, TPQEC, SFDB, MWR_SFDB, AVQ_SFDB, " +
|
||||||
|
"QEC_LIMIT, MWR_LIMIT, AVQ_LIMIT, QEC_C, MWR_C, AVQ_C, " +
|
||||||
|
"QEC_RULE_DID, QEC_MWRRULE_DID, SHOW_FLAG, IS_DELETED";
|
||||||
|
}
|
||||||
|
|
||||||
|
private String buildQecMonthLogSelectColumns() {
|
||||||
|
return "ID,STCD, DRTP, YEAR, MONTH, " +
|
||||||
|
"QEC, WATERFLOW, TPQEC, SFDB, MWR_SFDB, AVQ_SFDB, " +
|
||||||
|
"QEC_LIMIT, MWR_LIMIT, AVQ_LIMIT, QEC_C, MWR_C, AVQ_C, " +
|
||||||
|
"QEC_RULE_DID, QEC_MWRRULE_DID, SHOW_FLAG, IS_DELETED";
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Map<String, Object>> queryQecHourRows(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return new ArrayList<>();
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("SELECT ")
|
||||||
|
.append(buildQecHourLogSelectColumns())
|
||||||
|
.append(" FROM SD_QEC_R WHERE ");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
appendHourRowConditions(sql, params, dataParamList);
|
||||||
|
return normalizeLogRows(jdbcTemplate.queryForList(sql.toString(), params.toArray()));
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Map<String, Object>> queryQecDayRows(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return new ArrayList<>();
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("SELECT ")
|
||||||
|
.append(buildQecDayLogSelectColumns())
|
||||||
|
.append(" FROM SD_QECDAY_S WHERE ");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" OR ");
|
||||||
|
}
|
||||||
|
sql.append("(STCD = ? AND DT = TO_DATE(?, 'YYYY-MM-DD HH24:MI:SS'))");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getDt());
|
||||||
|
}
|
||||||
|
return normalizeLogRows(jdbcTemplate.queryForList(sql.toString(), params.toArray()));
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Map<String, Object>> queryQecMonthRows(List<DataParam> dataParamList) {
|
||||||
|
if (CollUtil.isEmpty(dataParamList)) {
|
||||||
|
return new ArrayList<>();
|
||||||
|
}
|
||||||
|
StringBuilder sql = new StringBuilder("SELECT ")
|
||||||
|
.append(buildQecMonthLogSelectColumns())
|
||||||
|
.append(" FROM SD_QECDRTP_S WHERE ");
|
||||||
|
List<Object> params = new ArrayList<>();
|
||||||
|
for (int i = 0; i < dataParamList.size(); i++) {
|
||||||
|
if (i > 0) {
|
||||||
|
sql.append(" OR ");
|
||||||
|
}
|
||||||
|
sql.append("(STCD = ? AND DRTP = ? AND YEAR = ? AND MONTH = ?)");
|
||||||
|
DataParam item = dataParamList.get(i);
|
||||||
|
params.add(item == null ? null : item.getId());
|
||||||
|
params.add(item == null ? null : item.getDrtp());
|
||||||
|
params.add(item == null ? null : item.getYear());
|
||||||
|
params.add(item == null ? null : item.getMonth());
|
||||||
|
}
|
||||||
|
return normalizeLogRows(jdbcTemplate.queryForList(sql.toString(), params.toArray()));
|
||||||
|
}
|
||||||
|
|
||||||
|
private List<Map<String, Object>> normalizeLogRows(List<Map<String, Object>> rows) {
|
||||||
|
List<Map<String, Object>> result = new ArrayList<>();
|
||||||
|
if (CollUtil.isEmpty(rows)) {
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
for (Map<String, Object> row : rows) {
|
||||||
|
result.add(normalizeLogRow(row));
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
private Map<String, Object> normalizeLogRow(Map<String, Object> row) {
|
||||||
|
Map<String, Object> normalized = new LinkedHashMap<>();
|
||||||
|
if (row == null || row.isEmpty()) {
|
||||||
|
return normalized;
|
||||||
|
}
|
||||||
|
for (Map.Entry<String, Object> entry : row.entrySet()) {
|
||||||
|
normalized.put(entry.getKey() == null ? null : entry.getKey().toUpperCase(), entry.getValue());
|
||||||
|
}
|
||||||
|
return normalized;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void recordQecDeleteLog(List<Map<String, Object>> rows, String tableName, String remark, String source) {
|
||||||
|
if (CollUtil.isEmpty(rows)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
List<MsOperationLogDetail> details = new ArrayList<>();
|
||||||
|
for (Map<String, Object> row : rows) {
|
||||||
|
String stcd = asString(row.get("STCD"));
|
||||||
|
String recordId = asString(row.get("ID"));
|
||||||
|
MsOperationLog mainLog = buildQecMainLog(recordId, remark, source,"03");
|
||||||
|
msOperationLogMapper.insert(mainLog);
|
||||||
|
for (Map.Entry<String, Object> entry : row.entrySet()) {
|
||||||
|
String fieldCode = entry.getKey();
|
||||||
|
if (StrUtil.isBlank(fieldCode)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
Object oldValue = entry.getValue();
|
||||||
|
if (oldValue == null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
details.add(buildQecDetail(mainLog.getId(), tableName, stcd, fieldCode,
|
||||||
|
oldValue, resolveQecDisplayValue(fieldCode, oldValue),
|
||||||
|
null, null, "删除字段值"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
batchInsertQecLogDetails(details);
|
||||||
|
}
|
||||||
|
|
||||||
|
private MsOperationLog buildQecMainLog(String recordId, String remark, String source,String operationType) {
|
||||||
|
MsOperationLog log = new MsOperationLog();
|
||||||
|
log.setOperator(resolveLogOperator());
|
||||||
|
log.setOperationType(operationType);
|
||||||
|
log.setRecordId(recordId);
|
||||||
|
log.setOperateTime(new Date());
|
||||||
|
log.setTableName(QEC_HOUR_TABLE_NAME);
|
||||||
|
log.setSource(StrUtil.trimToNull(source));
|
||||||
|
log.setRemark(remark);
|
||||||
|
return log;
|
||||||
|
}
|
||||||
|
|
||||||
|
private MsOperationLogDetail buildQecDetail(String mainId,
|
||||||
|
String tableName,
|
||||||
|
String stationCode,
|
||||||
|
String fieldCode,
|
||||||
|
Object oldValueCode,
|
||||||
|
Object oldValueName,
|
||||||
|
Object newValueCode,
|
||||||
|
Object newValueName,
|
||||||
|
String remark) {
|
||||||
|
MsOperationLogDetail detail = new MsOperationLogDetail();
|
||||||
|
detail.setMainId(mainId);
|
||||||
|
detail.setTableName(tableName);
|
||||||
|
detail.setStationCode(stationCode);
|
||||||
|
detail.setFieldCode(fieldCode);
|
||||||
|
detail.setFieldMeaning(QEC_FIELD_MEANING_MAP.getOrDefault(fieldCode, fieldCode));
|
||||||
|
detail.setOldValueCode(formatLogValue(oldValueCode));
|
||||||
|
detail.setOldValueName(formatLogValue(oldValueName));
|
||||||
|
detail.setNewValueCode(formatLogValue(newValueCode));
|
||||||
|
detail.setNewValueName(formatLogValue(newValueName));
|
||||||
|
detail.setRemark(remark);
|
||||||
|
return detail;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void batchInsertQecLogDetails(List<MsOperationLogDetail> details) {
|
||||||
|
if (CollUtil.isEmpty(details)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
for (MsOperationLogDetail detail : details) {
|
||||||
|
if (detail == null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
msOperationLogDetailMapper.insert(detail);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private Object resolveQecDisplayValue(String fieldCode, Object rawValue) {
|
||||||
|
String text = formatLogValue(rawValue);
|
||||||
|
if (StrUtil.isBlank(text)) {
|
||||||
|
return rawValue;
|
||||||
|
}
|
||||||
|
return switch (fieldCode) {
|
||||||
|
case "SFDB", "MWR_SFDB", "AVQ_SFDB" -> {
|
||||||
|
Integer val = parseInteger(text);
|
||||||
|
yield val == null ? text : getQecSfdbName(val);
|
||||||
|
}
|
||||||
|
case "SHOW_FLAG" -> {
|
||||||
|
Integer val = parseInteger(text);
|
||||||
|
yield val == null ? text : getShowFlagName(val);
|
||||||
|
}
|
||||||
|
default -> text;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
private String resolveLogOperator() {
|
||||||
|
try {
|
||||||
|
return SecurityUtils.getCurrentUsername();
|
||||||
|
} catch (Exception ignored) {
|
||||||
|
try {
|
||||||
|
return SecurityUtils.getUserId();
|
||||||
|
} catch (Exception ex) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String formatLogValue(Object value) {
|
||||||
|
if (value == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (value instanceof Date date) {
|
||||||
|
return DateUtil.formatDateTime(date);
|
||||||
|
}
|
||||||
|
return String.valueOf(value);
|
||||||
|
}
|
||||||
|
|
||||||
|
private Integer parseInteger(Object value) {
|
||||||
|
if (value == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return Integer.parseInt(String.valueOf(value));
|
||||||
|
} catch (NumberFormatException e) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String getQecSfdbName(Integer sfdb) {
|
||||||
|
if (sfdb == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return switch (sfdb) {
|
||||||
|
case 0 -> "不达标";
|
||||||
|
case 1 -> "达标";
|
||||||
|
case 2 -> "无生态流量数据";
|
||||||
|
case 3 -> "无生态流量限值要求";
|
||||||
|
default -> null;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
private String getShowFlagName(Integer showFlag) {
|
||||||
|
if (showFlag == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return switch (showFlag) {
|
||||||
|
case 1 -> "环保部";
|
||||||
|
case 2 -> "水利部";
|
||||||
|
case 3 -> "多年平均";
|
||||||
|
case 4 -> "无";
|
||||||
|
default -> null;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
private String getMonthEndDate(Integer year, Integer month) {
|
||||||
|
Calendar calendar = Calendar.getInstance();
|
||||||
|
calendar.set(year, month - 1, 1);
|
||||||
|
int lastDay = calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
|
||||||
|
return year + "-" + String.format("%02d", month) + "-" + String.format("%02d", lastDay);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 按站点+日期范围,用小时表(SD_QEC_R)重新聚合日表(SD_QECDAY_S)
|
||||||
|
* <p>当天小时数据已删空时,对应日表行被清除;否则按平均值重新聚合。</p>
|
||||||
|
*/
|
||||||
|
private void statisticsQecDayDataFromHour(String stcd, String startDate, String endDate) {
|
||||||
|
String deleteSql = "DELETE FROM SD_QECDAY_S T " +
|
||||||
|
"WHERE T.STCD = ? " +
|
||||||
|
"AND T.DT BETWEEN TO_DATE(?, 'YYYY-MM-DD') " +
|
||||||
|
"AND TO_DATE(?, 'YYYY-MM-DD') " +
|
||||||
|
"AND NOT EXISTS ( " +
|
||||||
|
"SELECT 1 FROM SD_QEC_R S " +
|
||||||
|
"WHERE S.STCD = T.STCD " +
|
||||||
|
"AND TRUNC(S.TM) = T.DT " +
|
||||||
|
"AND S.TM >= TO_DATE(? || ' 00:00:00', 'YYYY-MM-DD HH24:MI:SS') " +
|
||||||
|
"AND S.TM <= TO_DATE(? || ' 23:59:59', 'YYYY-MM-DD HH24:MI:SS') " +
|
||||||
|
"AND S.IS_DELETED = 0)";
|
||||||
|
jdbcTemplate.update(deleteSql, stcd, startDate, endDate, startDate, endDate);
|
||||||
|
|
||||||
|
String mergeSql = "MERGE INTO SD_QECDAY_S T " +
|
||||||
|
"USING ( " +
|
||||||
|
" SELECT " +
|
||||||
|
" STCD, " +
|
||||||
|
" TRUNC(TM) AS DT, " +
|
||||||
|
" AVG(QEC) AS QEC, " +
|
||||||
|
" AVG(WATERFLOW) AS WATERFLOW, " +
|
||||||
|
" MIN(SFDB) AS SFDB, " +
|
||||||
|
" MIN(MWR_SFDB) AS MWR_SFDB, " +
|
||||||
|
" MIN(AVQ_SFDB) AS AVQ_SFDB " +
|
||||||
|
" FROM SD_QEC_R " +
|
||||||
|
" WHERE STCD = ? " +
|
||||||
|
" AND TM >= TO_DATE(? || ' 00:00:00', 'YYYY-MM-DD HH24:MI:SS') " +
|
||||||
|
" AND TM <= TO_DATE(? || ' 23:59:59', 'YYYY-MM-DD HH24:MI:SS') " +
|
||||||
|
" AND IS_DELETED = 0 " +
|
||||||
|
" GROUP BY STCD, TRUNC(TM) " +
|
||||||
|
") S " +
|
||||||
|
"ON (T.STCD = S.STCD AND T.DT = S.DT) " +
|
||||||
|
"WHEN MATCHED THEN UPDATE SET " +
|
||||||
|
" T.QEC = S.QEC, " +
|
||||||
|
" T.WATERFLOW = S.WATERFLOW, " +
|
||||||
|
" T.SFDB = S.SFDB, " +
|
||||||
|
" T.MWR_SFDB = S.MWR_SFDB, " +
|
||||||
|
" T.AVQ_SFDB = S.AVQ_SFDB, " +
|
||||||
|
" T.IS_DELETED = 0, " +
|
||||||
|
" T.DELETE_USER = NULL, " +
|
||||||
|
" T.DELETE_TIME = NULL, " +
|
||||||
|
" T.MODIFY_USER = NULL, " +
|
||||||
|
" T.MODIFY_TIME = SYSDATE " +
|
||||||
|
"WHEN NOT MATCHED THEN INSERT ( " +
|
||||||
|
" ID, STCD, DT, QEC, WATERFLOW, SFDB, MWR_SFDB, AVQ_SFDB, " +
|
||||||
|
" RECORD_TIME, IS_DELETED " +
|
||||||
|
") VALUES ( " +
|
||||||
|
" SYS_GUID(), S.STCD, S.DT, S.QEC, S.WATERFLOW, S.SFDB, S.MWR_SFDB, S.AVQ_SFDB, " +
|
||||||
|
" SYSDATE, 0 " +
|
||||||
|
")";
|
||||||
|
jdbcTemplate.update(mergeSql, stcd, startDate, endDate);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 按站点+月份范围,用日表(SD_QECDAY_S)重新聚合循表月数据(SD_QECDRTP_S, DRTP='MON')
|
||||||
|
* <p>当月日数据已删空时,对应月数据行被清除;否则按平均值重新聚合。</p>
|
||||||
|
*/
|
||||||
|
private void statisticsQecMonthDataFromDay(String stcd, String startDate, String endDate) {
|
||||||
|
Integer startYearInt = Integer.parseInt(startDate.substring(0, 4));
|
||||||
|
Integer startMonthInt = Integer.parseInt(startDate.substring(5, 7));
|
||||||
|
Integer endMonthInt = Integer.parseInt(endDate.substring(5, 7));
|
||||||
|
|
||||||
|
String deleteSql = "DELETE FROM SD_QECDRTP_S T " +
|
||||||
|
"WHERE T.DRTP = 'MON' " +
|
||||||
|
"AND T.STCD = ? " +
|
||||||
|
"AND T.YEAR = ? " +
|
||||||
|
"AND T.MONTH BETWEEN ? AND ? " +
|
||||||
|
"AND NOT EXISTS ( " +
|
||||||
|
" SELECT 1 FROM SD_QECDAY_S D " +
|
||||||
|
" WHERE D.STCD = T.STCD " +
|
||||||
|
" AND D.IS_DELETED = 0 " +
|
||||||
|
" AND EXTRACT(YEAR FROM D.DT) = T.YEAR " +
|
||||||
|
" AND EXTRACT(MONTH FROM D.DT) = T.MONTH " +
|
||||||
|
" AND D.DT >= TO_DATE(?, 'YYYY-MM-DD') " +
|
||||||
|
" AND D.DT < TO_DATE(?, 'YYYY-MM-DD') + 1)";
|
||||||
|
jdbcTemplate.update(deleteSql, stcd, startYearInt, startMonthInt, endMonthInt, startDate, endDate);
|
||||||
|
|
||||||
|
String mergeSql = "MERGE INTO SD_QECDRTP_S T " +
|
||||||
|
"USING ( " +
|
||||||
|
" SELECT " +
|
||||||
|
" STCD, " +
|
||||||
|
" EXTRACT(YEAR FROM DT) AS YEAR, " +
|
||||||
|
" EXTRACT(MONTH FROM DT) AS MONTH, " +
|
||||||
|
" 'MON' AS DRTP, " +
|
||||||
|
" AVG(QEC) AS QEC, " +
|
||||||
|
" AVG(WATERFLOW) AS WATERFLOW, " +
|
||||||
|
" MIN(SFDB) AS SFDB, " +
|
||||||
|
" MIN(MWR_SFDB) AS MWR_SFDB, " +
|
||||||
|
" MIN(AVQ_SFDB) AS AVQ_SFDB " +
|
||||||
|
" FROM SD_QECDAY_S " +
|
||||||
|
" WHERE STCD = ? " +
|
||||||
|
" AND DT >= TO_DATE(?, 'YYYY-MM-DD') " +
|
||||||
|
" AND DT < TO_DATE(?, 'YYYY-MM-DD') + 1 " +
|
||||||
|
" AND IS_DELETED = 0 " +
|
||||||
|
" GROUP BY STCD, EXTRACT(YEAR FROM DT), EXTRACT(MONTH FROM DT) " +
|
||||||
|
") S " +
|
||||||
|
"ON (T.STCD = S.STCD AND T.DRTP = 'MON' AND T.YEAR = S.YEAR AND T.MONTH = S.MONTH) " +
|
||||||
|
"WHEN MATCHED THEN UPDATE SET " +
|
||||||
|
" T.QEC = S.QEC, " +
|
||||||
|
" T.WATERFLOW = S.WATERFLOW, " +
|
||||||
|
" T.SFDB = S.SFDB, " +
|
||||||
|
" T.MWR_SFDB = S.MWR_SFDB, " +
|
||||||
|
" T.AVQ_SFDB = S.AVQ_SFDB, " +
|
||||||
|
" T.IS_DELETED = 0, " +
|
||||||
|
" T.DELETE_TIME = NULL, " +
|
||||||
|
" T.MODIFY_TIME = SYSDATE " +
|
||||||
|
"WHEN NOT MATCHED THEN INSERT ( " +
|
||||||
|
" ID, STCD, DRTP, YEAR, MONTH, TM, QEC, WATERFLOW, SFDB, MWR_SFDB, AVQ_SFDB, " +
|
||||||
|
" RECORD_TIME, IS_DELETED " +
|
||||||
|
") VALUES ( " +
|
||||||
|
" SYS_GUID(), S.STCD, 'MON', S.YEAR, S.MONTH, " +
|
||||||
|
" TO_DATE(S.YEAR || '-' || S.MONTH || '-01', 'YYYY-MM-DD'), " +
|
||||||
|
" S.QEC, S.WATERFLOW, S.SFDB, S.MWR_SFDB, S.AVQ_SFDB, " +
|
||||||
|
" SYSDATE, 0 " +
|
||||||
|
")";
|
||||||
|
jdbcTemplate.update(mergeSql, stcd, startDate, endDate);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user