From abb76a8abbdce4279f47845e78b81526d9e009a9 Mon Sep 17 00:00:00 2001 From: tangwei Date: Fri, 12 Jun 2026 15:34:21 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=80=BB=E9=99=A2=E9=B1=BC=E7=B1=BB?= =?UTF-8?q?=E5=AD=97=E5=85=B8=E5=88=97=E8=A1=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../fpr/controller/FprMonitorController.java | 7 + .../qgc_env/fpr/entity/vo/FprZyFishDicVo.java | 46 +++ .../fpr/service/FprMonitorService.java | 3 + .../service/impl/FprMonitorServiceImpl.java | 316 ++++++++++++++++++ 4 files changed, 372 insertions(+) create mode 100644 backend/src/main/java/com/yfd/platform/qgc_env/fpr/entity/vo/FprZyFishDicVo.java diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/controller/FprMonitorController.java b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/controller/FprMonitorController.java index 49d3cf87..a5f31b87 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/controller/FprMonitorController.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/controller/FprMonitorController.java @@ -6,6 +6,7 @@ import com.yfd.platform.qgc_env.fpr.entity.ao.FprdRunDataAo; import com.yfd.platform.qgc_eng.eq.service.EngEqDataService; import com.yfd.platform.qgc_env.fpr.entity.vo.FprFtpChangeInfoVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprdRunDataInfoVo; +import com.yfd.platform.qgc_env.fpr.entity.vo.FprZyFishDicVo; import com.yfd.platform.qgc_env.fpr.service.FprMonitorService; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.tags.Tag; @@ -43,6 +44,12 @@ public class FprMonitorController { return ResponseResult.successData(fprMonitorService.getFishDicList(dataSourceRequest)); } + @PostMapping("/fishDic/zy/GetKendoList") + @Operation(summary = "总院鱼类字典列表") + public ResponseResult getZyFishDicList(@RequestBody DataSourceRequest dataSourceRequest) { + return ResponseResult.successData(fprMonitorService.getZyFishDicList(dataSourceRequest)); + } + @PostMapping("/sdFprdR/getFprdDataInfo") @Operation(summary = "获取鱼类调查装置概况") public ResponseResult getFprdRunDataInfo(@RequestBody FprdRunDataAo ao) { diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/entity/vo/FprZyFishDicVo.java b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/entity/vo/FprZyFishDicVo.java new file mode 100644 index 00000000..6399d079 --- /dev/null +++ b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/entity/vo/FprZyFishDicVo.java @@ -0,0 +1,46 @@ +package com.yfd.platform.qgc_env.fpr.entity.vo; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +@Data +@Schema(description = "总院鱼类字典信息") +public class FprZyFishDicVo { + + private Integer index; + private String id; + private Integer isDeleted; + private String zyFishId; + private String rvcd; + private String rvcdName; + private String name; + private Integer type; + private String family; + private String genus; + private String species; + private String nameEn; + private String alias; + private String fsz; + private String shapedesc; + private String habitation; + private String habitMigrat; + private String feedingHabit; + private String food; + private String timeFeed; + private String orignDate; + private String filterContent; + private String pretemp; + private String flowRate; + private String depth; + private String wqtq; + private String spawnCharact; + private String botmMater; + private Integer ptype; + private String ptypeName; + private Integer specOrigin; + private String specOriginName; + private String description; + private String logo; + private String inffile; + private String spawnMonth; +} diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/FprMonitorService.java b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/FprMonitorService.java index 9f638034..c0c49dd4 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/FprMonitorService.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/FprMonitorService.java @@ -7,6 +7,7 @@ import com.yfd.platform.qgc_env.fpr.entity.ao.FprdRunDataAo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprFishDicVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprMsstbprptVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprdRunDataInfoVo; +import com.yfd.platform.qgc_env.fpr.entity.vo.FprZyFishDicVo; import java.util.List; @@ -16,6 +17,8 @@ public interface FprMonitorService { DataSourceResult getFishDicList(DataSourceRequest dataSourceRequest); + DataSourceResult getZyFishDicList(DataSourceRequest dataSourceRequest); + FprdRunDataInfoVo getFprdRunDataInfo(FprdRunDataAo ao); List getFtpChangeInfo(FprdRunDataAo ao); diff --git a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/impl/FprMonitorServiceImpl.java b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/impl/FprMonitorServiceImpl.java index 309e6f0e..993da4ea 100644 --- a/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/impl/FprMonitorServiceImpl.java +++ b/backend/src/main/java/com/yfd/platform/qgc_env/fpr/service/impl/FprMonitorServiceImpl.java @@ -17,6 +17,7 @@ import com.yfd.platform.qgc_env.fpr.entity.vo.FprFishDicVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprFtpChangeInfoVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprMsstbprptVo; import com.yfd.platform.qgc_env.fpr.entity.vo.FprdRunDataInfoVo; +import com.yfd.platform.qgc_env.fpr.entity.vo.FprZyFishDicVo; import com.yfd.platform.qgc_env.fpr.service.FprMonitorService; import com.yfd.platform.utils.QgcQueryWrapperUtil; import jakarta.annotation.Resource; @@ -28,6 +29,7 @@ import java.util.HashMap; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; +import java.util.stream.Collectors; @Service public class FprMonitorServiceImpl implements FprMonitorService { @@ -182,6 +184,89 @@ public class FprMonitorServiceImpl implements FprMonitorService { return result; } + @Override + public DataSourceResult getZyFishDicList(DataSourceRequest dataSourceRequest) { + DataSourceLoadOptionsBase loadOptions = dataSourceRequest == null ? null : dataSourceRequest.toDevRequest(); + Map paramMap = new HashMap<>(); + String rvcd = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "rvcd"); + String filterSql = buildZyFishDicFilterCondition( + dataSourceRequest == null ? null : dataSourceRequest.getFilter(), + paramMap, + new int[]{0} + ); + + StringBuilder sql = new StringBuilder("SELECT * FROM (") + .append(buildZyFishDicBaseSql()) + .append(") t WHERE 1 = 1 "); + if (StrUtil.isNotBlank(filterSql)) { + sql.append(" AND ").append(filterSql).append(" "); + } + + List list = microservicDynamicSQLMapper.getAllListWithResultType( + sql.toString(), + paramMap, + FprZyFishDicVo.class + ); + List> rvcdRows = microservicDynamicSQLMapper.getAllList( + "SELECT RVCD AS rvcd, RVNM AS rvcdName FROM SD_RVCD_DIC", + null + ); + Map rvcdNameMap = new HashMap<>(); + for (Map row : rvcdRows) { + Object rvcdKey = row.get("RVCD"); + Object rvcdName = row.get("RVCDNAME"); + if (rvcdKey != null && rvcdName != null) { + rvcdNameMap.put(String.valueOf(rvcdKey), String.valueOf(rvcdName)); + } + } + + List resultList; + Map> rvcdMap = new HashMap<>(); + if (StrUtil.isBlank(rvcd)) { + rvcdMap = list.stream() + .collect(Collectors.groupingBy( + item -> StrUtil.blankToDefault(item.getZyFishId(), item.getId()), + LinkedHashMap::new, + Collectors.mapping(FprZyFishDicVo::getRvcd, Collectors.toList()) + )); + LinkedHashMap distinctMap = new LinkedHashMap<>(); + for (FprZyFishDicVo item : list) { + distinctMap.putIfAbsent(StrUtil.blankToDefault(item.getZyFishId(), item.getId()), item); + } + resultList = new ArrayList<>(distinctMap.values()); + } else { + resultList = new ArrayList<>(list); + } + + for (int i = 0; i < resultList.size(); i++) { + FprZyFishDicVo item = resultList.get(i); + item.setIndex(i + 1); + item.setSpawnMonth(formatSpawnMonth(item.getSpawnMonth())); + if (StrUtil.isBlank(rvcd)) { + List rvcdList = rvcdMap.getOrDefault( + StrUtil.blankToDefault(item.getZyFishId(), item.getId()), + new ArrayList<>() + ).stream().filter(StrUtil::isNotBlank).distinct().toList(); + List rvcdNames = new ArrayList<>(); + for (String rvcdItem : rvcdList) { + String rvcdName = rvcdNameMap.get(rvcdItem); + if (StrUtil.isNotBlank(rvcdName)) { + rvcdNames.add(rvcdName); + } + } + item.setRvcdName(String.join(",", rvcdNames)); + } else { + item.setRvcdName(rvcdNameMap.get(item.getRvcd())); + } + } + + DataSourceResult result = new DataSourceResult<>(); + result.setTotal((long) resultList.size()); + result.setData(paginateZyFishDicList(resultList, loadOptions)); + result.setAggregates(new HashMap<>()); + return result; + } + private String buildMsstbprptBaseSql() { return "SELECT " + "CAST(NULL AS VARCHAR2(36)) AS id, " + @@ -415,6 +500,49 @@ public class FprMonitorServiceImpl implements FprMonitorService { "WHERE NVL(src.IS_DELETED, 0) = 0 "; } + private String buildZyFishDicBaseSql() { + return "SELECT DISTINCT " + + "src.ID AS id, " + + "NVL(src.IS_DELETED, 0) AS isDeleted, " + + "CASE WHEN rel.ZY_FISH_ID IS NULL THEN src.ID ELSE rel.ZY_FISH_ID END AS zyFishId, " + + "CASE WHEN rel.RVCD IS NULL THEN 'null' ELSE rel.RVCD END AS rvcd, " + + "src.NAME AS name, " + + "src.TYPE AS type, " + + "src.FAMILY AS family, " + + "src.GENUS AS genus, " + + "src.SPECIES AS species, " + + "src.NAME_EN AS nameEn, " + + "src.ALIAS AS alias, " + + "src.FSZ AS fsz, " + + "src.SHAPEDESC AS shapedesc, " + + "src.HABITATION AS habitation, " + + "src.HABIT_MIGRAT AS habitMigrat, " + + "src.FEEDING_HABIT AS feedingHabit, " + + "src.FOOD AS food, " + + "src.TIME_FEED AS timeFeed, " + + "src.ORIGN_DATE AS orignDate, " + + "CAST(NULL AS VARCHAR2(255)) AS filterContent, " + + "src.PRETEMP AS pretemp, " + + "src.FLOW_RATE AS flowRate, " + + "src.DEPTH AS depth, " + + "src.WQTQ AS wqtq, " + + "src.SPAWN_CHARACT AS spawnCharact, " + + "src.BOTM_MATER AS botmMater, " + + "src.PTYPE AS ptype, " + + "CASE src.PTYPE WHEN 1 THEN '濒危' WHEN 2 THEN '极危' WHEN 3 THEN '近危' WHEN 4 THEN '易危' WHEN 5 THEN '重点保护' WHEN 6 THEN '无危' WHEN 7 THEN '国家二级' WHEN 8 THEN '市二级保护' ELSE '未知' END AS ptypeName, "+ + "src.SPEC_ORIGIN AS specOrigin, " + + "CASE WHEN src.SPEC_ORIGIN = 1 THEN '本土物种' WHEN src.SPEC_ORIGIN = 2 THEN '外来物种' ELSE NULL END AS specOriginName, " + + "src.DESCRIPTION AS description, " + + "src.LOGO AS logo, " + + "src.INFFILE AS inffile, " + + "src.SPAWN_MONTH AS spawnMonth " + + "FROM SD_FISHDICTORY_B src " + + "LEFT JOIN SD_FISHDICTORY_RLTN_B rel ON src.ID = rel.ZY_FISH_ID " + + " AND rel.RVCD <> 'ZY' " + + " AND NVL(rel.IS_DELETED, 0) = 0 " + + "WHERE NVL(src.IS_DELETED, 0) = 0 "; + } + private String buildMsstbprptDetailSelectSql(List selectFields) { LinkedHashMap columnMap = buildMsstbprptSelectColumnMap(); if (CollUtil.isEmpty(selectFields)) { @@ -619,6 +747,31 @@ public class FprMonitorServiceImpl implements FprMonitorService { return String.join("or".equalsIgnoreCase(filter.getLogic()) ? " OR " : " AND ", conditions); } + private String buildZyFishDicFilterCondition(DataSourceRequest.FilterDescriptor filter, + Map paramMap, + int[] indexHolder) { + if (filter == null) { + return ""; + } + if (StrUtil.isNotBlank(filter.getField())) { + return buildZyFishDicLeafCondition(filter, paramMap, indexHolder); + } + if (filter.getFilters() == null || filter.getFilters().isEmpty()) { + return ""; + } + List conditions = new ArrayList<>(); + for (DataSourceRequest.FilterDescriptor child : filter.getFilters()) { + String childSql = buildZyFishDicFilterCondition(child, paramMap, indexHolder); + if (StrUtil.isNotBlank(childSql)) { + conditions.add("(" + childSql + ")"); + } + } + if (conditions.isEmpty()) { + return ""; + } + return String.join("or".equalsIgnoreCase(filter.getLogic()) ? " OR " : " AND ", conditions); + } + private String buildMsstbprptLeafCondition(DataSourceRequest.FilterDescriptor filter, Map paramMap, int[] indexHolder) { @@ -771,6 +924,90 @@ public class FprMonitorServiceImpl implements FprMonitorService { } } + private String buildZyFishDicLeafCondition(DataSourceRequest.FilterDescriptor filter, + Map paramMap, + int[] indexHolder) { + String field = filter.getField(); + String operator = StrUtil.blankToDefault(filter.getOperator(), "eq").toLowerCase(); + Object value = filter.getValue(); + + if ("keyword".equals(field)) { + if (value == null || StrUtil.isBlank(String.valueOf(value))) { + return ""; + } + String paramKey = "fprZyP" + indexHolder[0]++; + paramMap.put(paramKey, "%" + value + "%"); + return "(t.name LIKE #{map." + paramKey + "} " + + "OR t.nameEn LIKE #{map." + paramKey + "} " + + "OR t.alias LIKE #{map." + paramKey + "} " + + "OR t.family LIKE #{map." + paramKey + "} " + + "OR t.genus LIKE #{map." + paramKey + "} " + + "OR t.species LIKE #{map." + paramKey + "})"; + } + + String column = mapZyFishDicColumn(field); + if (StrUtil.isBlank(column)) { + return ""; + } + if ("isnull".equals(operator)) { + return column + " IS NULL"; + } + if ("isnotnull".equals(operator)) { + return column + " IS NOT NULL"; + } + if ("in".equals(operator)) { + List values = normalizeValues(value); + if (values.isEmpty()) { + return ""; + } + List placeholders = new ArrayList<>(); + for (Object item : values) { + String paramKey = "fprZyP" + indexHolder[0]++; + paramMap.put(paramKey, item); + placeholders.add("#{map." + paramKey + "}"); + } + return column + " IN (" + String.join(", ", placeholders) + ")"; + } + if (value == null) { + return ""; + } + String paramKey = "fprZyP" + indexHolder[0]++; + switch (operator) { + case "eq": + paramMap.put(paramKey, value); + return column + " = #{map." + paramKey + "}"; + case "neq": + paramMap.put(paramKey, value); + return column + " <> #{map." + paramKey + "}"; + case "contains": + paramMap.put(paramKey, "%" + value + "%"); + return column + " LIKE #{map." + paramKey + "}"; + case "notcontains": + paramMap.put(paramKey, "%" + value + "%"); + return column + " NOT LIKE #{map." + paramKey + "}"; + case "startswith": + paramMap.put(paramKey, value + "%"); + return column + " LIKE #{map." + paramKey + "}"; + case "endswith": + paramMap.put(paramKey, "%" + value); + return column + " LIKE #{map." + paramKey + "}"; + case "gt": + paramMap.put(paramKey, value); + return column + " > #{map." + paramKey + "}"; + case "gte": + paramMap.put(paramKey, value); + return column + " >= #{map." + paramKey + "}"; + case "lt": + paramMap.put(paramKey, value); + return column + " < #{map." + paramKey + "}"; + case "lte": + paramMap.put(paramKey, value); + return column + " <= #{map." + paramKey + "}"; + default: + return ""; + } + } + private String mapMsstbprptColumn(String field) { if (StrUtil.isBlank(field)) { return null; @@ -903,6 +1140,85 @@ public class FprMonitorServiceImpl implements FprMonitorService { }; } + private String mapZyFishDicColumn(String field) { + if (StrUtil.isBlank(field)) { + return null; + } + return switch (field) { + case "id" -> "t.id"; + case "isDeleted" -> "t.isDeleted"; + case "zyFishId" -> "t.zyFishId"; + case "rvcd" -> "t.rvcd"; + case "name" -> "t.name"; + case "type" -> "t.type"; + case "family" -> "t.family"; + case "genus" -> "t.genus"; + case "species" -> "t.species"; + case "nameEn" -> "t.nameEn"; + case "alias" -> "t.alias"; + case "fsz" -> "t.fsz"; + case "shapedesc" -> "t.shapedesc"; + case "habitation" -> "t.habitation"; + case "habitMigrat" -> "t.habitMigrat"; + case "feedingHabit" -> "t.feedingHabit"; + case "food" -> "t.food"; + case "timeFeed" -> "t.timeFeed"; + case "orignDate" -> "t.orignDate"; + case "filterContent" -> "t.filterContent"; + case "pretemp" -> "t.pretemp"; + case "flowRate" -> "t.flowRate"; + case "depth" -> "t.depth"; + case "wqtq" -> "t.wqtq"; + case "spawnCharact" -> "t.spawnCharact"; + case "botmMater" -> "t.botmMater"; + case "ptype" -> "t.ptype"; + case "specOrigin" -> "t.specOrigin"; + case "description" -> "t.description"; + case "logo" -> "t.logo"; + case "inffile" -> "t.inffile"; + case "spawnMonth" -> "t.spawnMonth"; + default -> null; + }; + } + + private List paginateZyFishDicList(List resultList, DataSourceLoadOptionsBase loadOptions) { + if (CollUtil.isEmpty(resultList) || loadOptions == null || loadOptions.getTake() == null || loadOptions.getTake() <= 0) { + return resultList; + } + int start = Math.max(loadOptions.getSkip() == null ? 0 : loadOptions.getSkip(), 0); + int end = Math.min(start + loadOptions.getTake(), resultList.size()); + if (start >= resultList.size()) { + return new ArrayList<>(); + } + return new ArrayList<>(resultList.subList(start, end)); + } + + private String formatSpawnMonth(String input) { + if (StrUtil.isBlank(input)) { + return input; + } + try { + String[] numbers = input.split(","); + List ranges = new ArrayList<>(); + int start = Integer.parseInt(numbers[0]); + int end = Integer.parseInt(numbers[0]); + for (int i = 1; i < numbers.length; i++) { + int current = Integer.parseInt(numbers[i]); + if (current == end + 1) { + end = current; + } else { + ranges.add(start == end ? Integer.toString(start) : start + "-" + end); + start = current; + end = current; + } + } + ranges.add(start == end ? Integer.toString(start) : start + "-" + end); + return String.join(",", ranges); + } catch (Exception ex) { + return input; + } + } + private String buildMsstbprptDetailOrderBySql(List sorts) { List orderItems = new ArrayList<>(); if (CollUtil.isNotEmpty(sorts)) {