From 158f33177744abd9d15eb3aee7d0785693d821c7 Mon Sep 17 00:00:00 2001 From: tangwei Date: Tue, 23 Jun 2026 18:01:36 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=85=A8=E8=BF=87=E7=A8=8BAI=E8=AF=86?= =?UTF-8?q?=E5=88=AB=E7=9B=91=E6=B5=8B=E6=97=A5=E5=8E=86=E8=A1=A8(?= =?UTF-8?q?=E6=BC=82=E6=B5=AE=E7=89=A9+=E6=B8=85=E6=BC=82=E5=90=88?= =?UTF-8?q?=E5=B9=B6)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../warn/controller/WarnDataController.java | 6 + .../qgc_env/warn/entity/vo/AiRecordVo.java | 44 ++++++ .../qgc_env/warn/service/WarnDataService.java | 5 + .../service/impl/WarnDataServiceImpl.java | 140 +++++++++++++++++- 4 files changed, 194 insertions(+), 1 deletion(-) create mode 100644 backend/src/main/java/com/yfd/platform/qgc_env/warn/entity/vo/AiRecordVo.java diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/warn/controller/WarnDataController.java b/backend/src/main/java/com/yfd/platform/qgc_env/warn/controller/WarnDataController.java index 223aa53d..7b3bf630 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/warn/controller/WarnDataController.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/warn/controller/WarnDataController.java @@ -50,4 +50,10 @@ public class WarnDataController { public ResponseResult getAiRstcdListKendoListCust(@RequestBody DataSourceRequest dataSourceRequest) { return ResponseResult.successData(warnDataService.getAiRstcdListKendoListCust(dataSourceRequest)); } + + @PostMapping("/ai/com/qgc/aiPfwRecord/GetKendoListCust") + @Operation(summary = "全过程AI识别监测日历表(漂浮物+清漂合并)") + public ResponseResult getAiPfwRecordKendoListCust(@RequestBody DataSourceRequest dataSourceRequest) { + return ResponseResult.successData(warnDataService.getAiPfwRecordKendoListCust(dataSourceRequest)); + } } diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/warn/entity/vo/AiRecordVo.java b/backend/src/main/java/com/yfd/platform/qgc_env/warn/entity/vo/AiRecordVo.java new file mode 100644 index 00000000..dfe4d0e3 --- /dev/null +++ b/backend/src/main/java/com/yfd/platform/qgc_env/warn/entity/vo/AiRecordVo.java @@ -0,0 +1,44 @@ +package com.yfd.platform.qgc_env.warn.entity.vo; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; +import lombok.experimental.Accessors; + +@Data +@Accessors(chain = true) +@Schema(description = "全过程AI识别监测日历记录") +public class AiRecordVo { + + @Schema(description = "AI类型") + private String type; + + @Schema(description = "日期") + private String dt; + + @Schema(description = "是否大面积漂浮物") + private Integer isBigDebrisArea; + + @Schema(description = "AI数据数") + private Integer aiCnt; + + @Schema(description = "统计数") + private Integer cnt; + + @Schema(description = "是否已清漂") + private Integer isClearDrift; + + @Schema(description = "漂浮物状态") + private Integer status; + + @Schema(description = "漂浮物状态名称") + private String statusName; + + @Schema(description = "清漂状态") + private Integer qpStatus; + + @Schema(description = "清漂状态名称") + private String qpStatusName; + + @Schema(description = "附件ID") + private String fid; +} diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/WarnDataService.java b/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/WarnDataService.java index fd640f6f..99706afa 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/WarnDataService.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/WarnDataService.java @@ -2,12 +2,15 @@ package com.yfd.platform.qgc_env.warn.service; import com.yfd.platform.common.DataSourceRequest; import com.yfd.platform.common.DataSourceResult; +import com.yfd.platform.qgc_env.warn.entity.vo.AiRecordVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiProtectVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiDmRunVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiComListVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiRstcdVo; import com.yfd.platform.qgc_env.warn.entity.vo.EngWarnCountVo; +import java.util.List; + public interface WarnDataService { DataSourceResult getEngWarnCount(DataSourceRequest dataSourceRequest); @@ -19,4 +22,6 @@ public interface WarnDataService { DataSourceResult getAiComKendoListCust(DataSourceRequest dataSourceRequest); DataSourceResult getAiRstcdListKendoListCust(DataSourceRequest dataSourceRequest); + + List getAiPfwRecordKendoListCust(DataSourceRequest dataSourceRequest); } diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/impl/WarnDataServiceImpl.java b/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/impl/WarnDataServiceImpl.java index d454814d..98b1eebf 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/impl/WarnDataServiceImpl.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/warn/service/impl/WarnDataServiceImpl.java @@ -13,7 +13,7 @@ import com.yfd.platform.common.MicroservicDynamicSQLMapper; import com.yfd.platform.qgc_env.warn.entity.vo.AiComListVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiDmRunVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiProtectVo; -import com.yfd.platform.qgc_env.warn.entity.vo.AiProtectVo; +import com.yfd.platform.qgc_env.warn.entity.vo.AiRecordVo; import com.yfd.platform.qgc_env.warn.entity.vo.AiRstcdVo; import com.yfd.platform.qgc_env.warn.entity.vo.EngWarnCountVo; import com.yfd.platform.qgc_env.warn.service.WarnDataService; @@ -221,6 +221,21 @@ public class WarnDataServiceImpl implements WarnDataService { return result; } + @Override + public List getAiPfwRecordKendoListCust(DataSourceRequest dataSourceRequest) { + DataSourceLoadOptionsBase loadOptions = dataSourceRequest == null ? null : dataSourceRequest.toDevRequest(); + String baseId = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "baseId"); + String startTime = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "startTime"); + String endTime = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "endTime"); + String rstcd = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "rstcd"); + + Map paramMap = new HashMap<>(); + String sql = buildAiPfwRecordSql(baseId, parseAiTime(startTime), parseAiTime(endTime), parseAiCodes(rstcd), paramMap); + List list = microservicDynamicSQLMapper.getAllListWithResultType(sql, paramMap, AiRecordVo.class); + fillAiPfwStatus(list); + return list; + } + private AiDmRunVo buildAiDmRunVo(Map row) { if (row == null || row.isEmpty()) { return null; @@ -264,6 +279,53 @@ public class WarnDataServiceImpl implements WarnDataService { return sql.toString(); } + private String buildAiPfwRecordSql(String baseId, + Date startTime, + Date endTime, + List rstcdList, + Map paramMap) { + StringBuilder sql = new StringBuilder(); + sql.append("SELECT a.dt AS dt, b.isClearDrift AS isClearDrift, b.isBigDebrisArea AS isBigDebrisArea, b.fid AS fid ") + .append("FROM (") + .append("SELECT TO_CHAR(hb.TM, 'yyyy-MM-dd') AS dt ") + .append("FROM SD_AIHEARTBEAT_R hb ") + .append("INNER JOIN SD_AIMONITOR_B_H ai ON ai.STCD = hb.STCD ") + .append("WHERE NVL(hb.IS_DELETED, 0) = 0 ") + .append("AND NVL(ai.IS_DELETED, 0) = 0 ") + .append("AND ai.STTP = 'AI_5001' "); + appendAiPfwFacilityFilterSql(sql, "aiPfwHeartbeat", "ai", "hb", baseId, startTime, endTime, rstcdList, paramMap); + sql.append("GROUP BY TO_CHAR(hb.TM, 'yyyy-MM-dd') ") + .append("UNION ") + .append("SELECT TO_CHAR(rec.TM, 'yyyy-MM-dd') AS dt ") + .append("FROM SD_AICOM_R rec ") + .append("INNER JOIN SD_AIMONITOR_B_H ai ON ai.STCD = rec.STCD ") + .append("WHERE NVL(rec.IS_DELETED, 0) = 0 ") + .append("AND NVL(ai.IS_DELETED, 0) = 0 ") + .append("AND ai.STTP = 'AI_5001' "); + appendAiPfwFacilityFilterSql(sql, "aiPfwAicom", "ai", "rec", baseId, startTime, endTime, rstcdList, paramMap); + sql.append("GROUP BY TO_CHAR(rec.TM, 'yyyy-MM-dd') ") + .append(") a ") + .append("LEFT JOIN (") + .append("SELECT TO_CHAR(rec.TM, 'yyyy-MM-dd') AS dt, ") + .append("MAX(CASE ") + .append("WHEN rec.TYPE = 'AI_5001' AND rec.IS_BIG_DEBRIS_AREA IS NULL THEN 0 ") + .append("WHEN rec.TYPE = 'AI_5001' AND rec.IS_BIG_DEBRIS_AREA IS NOT NULL THEN rec.IS_BIG_DEBRIS_AREA ") + .append("END) AS isBigDebrisArea, ") + .append("MAX(CASE WHEN rec.TYPE = 'AI_5011' THEN 1 END) AS isClearDrift, ") + .append("LISTAGG(rec.FID, ',') WITHIN GROUP (ORDER BY rec.FID) AS fid ") + .append("FROM SD_AICOM_R rec ") + .append("INNER JOIN SD_AIMONITOR_B_H ai ON ai.STCD = rec.STCD ") + .append("WHERE NVL(rec.IS_DELETED, 0) = 0 ") + .append("AND NVL(ai.IS_DELETED, 0) = 0 ") + .append("AND ai.STTP = 'AI_5001' ") + .append("AND rec.TYPE IN ('AI_5001', 'AI_5011') "); + appendAiPfwFacilityFilterSql(sql, "aiPfwStatus", "ai", "rec", baseId, startTime, endTime, rstcdList, paramMap); + sql.append("GROUP BY TO_CHAR(rec.TM, 'yyyy-MM-dd') ") + .append(") b ON a.dt = b.dt ") + .append("ORDER BY a.dt"); + return sql.toString(); + } + private void appendAiRstcdCommonFilterSql(StringBuilder sql, String keyPrefix, String aiAlias, @@ -313,6 +375,82 @@ public class WarnDataServiceImpl implements WarnDataService { sql.append("AND ai.STTP = #{map.aiRstcdHeartbeatType} "); } + private void appendAiPfwFacilityFilterSql(StringBuilder sql, + String keyPrefix, + String aiAlias, + String recordAlias, + String baseId, + Date startTime, + Date endTime, + List rstcdList, + Map paramMap) { + if (StrUtil.isNotBlank(baseId)) { + paramMap.put(keyPrefix + "BaseId", baseId.trim()); + sql.append("AND ").append(aiAlias).append(".BASE_ID = #{map.").append(keyPrefix).append("BaseId} "); + } + if (CollUtil.isNotEmpty(rstcdList)) { + List placeholders = new ArrayList<>(); + for (int i = 0; i < rstcdList.size(); i++) { + String key = keyPrefix + "Rstcd" + i; + paramMap.put(key, rstcdList.get(i)); + placeholders.add("#{map." + key + "}"); + } + sql.append("AND ").append(aiAlias).append(".RSTCD IN (").append(String.join(", ", placeholders)).append(") "); + } + if (startTime != null) { + paramMap.put(keyPrefix + "StartTime", startTime); + sql.append("AND ").append(recordAlias).append(".TM >= #{map.").append(keyPrefix).append("StartTime} "); + } + if (endTime != null) { + paramMap.put(keyPrefix + "EndTime", endTime); + sql.append("AND ").append(recordAlias).append(".TM <= #{map.").append(keyPrefix).append("EndTime} "); + } + } + + private void fillAiPfwStatus(List list) { + if (CollUtil.isEmpty(list)) { + return; + } + for (AiRecordVo item : list) { + if (item == null) { + continue; + } + if (item.getIsBigDebrisArea() != null) { + if (item.getIsBigDebrisArea() == 0) { + item.setStatus(1); + } else { + item.setStatus(2); + } + } else { + item.setStatus(0); + } + item.setStatusName(resolveAiStatusName(item.getStatus())); + if (item.getIsClearDrift() != null) { + item.setQpStatus(5); + } else { + item.setQpStatus(6); + } + item.setQpStatusName(resolveAiStatusName(item.getQpStatus())); + } + } + + private String resolveAiStatusName(Integer status) { + if (status == null) { + return null; + } + return switch (status) { + case -1 -> "未监测"; + case 0 -> "无漂浮物"; + case 1 -> "小面积漂浮物"; + case 2 -> "大面积漂浮物"; + case 3 -> "运行"; + case 4 -> "未运行"; + case 5 -> "清漂"; + case 6 -> "未清漂"; + default -> null; + }; + } + private AiProtectVo buildAiProtectVo(Map row) { if (row == null || row.isEmpty()) { return null;