feat: 查询水温指定时间有数据的站点-树形结构

This commit is contained in:
tangwei 2026-05-27 11:02:23 +08:00
parent 684eb621e4
commit b6f6c6e8d3
5 changed files with 377 additions and 2 deletions

View File

@ -185,6 +185,12 @@ public class SdWTMonitorController {
return ResponseResult.successData(sdWtvtRService.getWtrvDefaultYear(dataSourceRequest)); return ResponseResult.successData(sdWtvtRService.getWtrvDefaultYear(dataSourceRequest));
} }
@PostMapping("/sdrvwts/default/treeStcd")
@Operation(summary = "查询水温指定时间有数据的站点-树形结构")
public ResponseResult getWtvtDefaultTreeStcd(@RequestBody DataSourceRequest dataSourceRequest) {
return ResponseResult.successData(sdWtMonitorService.getWtvtDefaultTreeStcd(dataSourceRequest));
}
@PostMapping("/wtrv/fish/GetKendoListCust") @PostMapping("/wtrv/fish/GetKendoListCust")
@Operation(summary = "鱼类繁殖适宜性分析") @Operation(summary = "鱼类繁殖适宜性分析")
public ResponseResult getWtFishAnalysis(@RequestBody DataSourceRequest dataSourceRequest) { public ResponseResult getWtFishAnalysis(@RequestBody DataSourceRequest dataSourceRequest) {

View File

@ -0,0 +1,24 @@
package com.yfd.platform.env.wt.entity.vo;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
@Data
@Schema(description = "电站-站点树形结构")
public class RstcdTreeInfoVo implements Serializable {
private static final long serialVersionUID = 1L;
@Schema(description = "电站编码")
private String rstcd;
@Schema(description = "电站名称")
private String ennm;
@Schema(description = "测站数据")
private List<WtTreeStcdVo> stcdVo = new ArrayList<>();
}

View File

@ -0,0 +1,58 @@
package com.yfd.platform.env.wt.entity.vo;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.io.Serializable;
@Data
@Schema(description = "垂向水温树形站点")
public class WtTreeStcdVo implements Serializable {
private static final long serialVersionUID = 1L;
@Schema(description = "站码")
private String stcd;
@Schema(description = "站名")
private String stnm;
@Schema(description = "电站排序")
private Integer rstcdStepSort;
@Schema(description = "所属电站编码")
private String rstcd;
@Schema(description = "所属电站名称")
private String ennm;
@Schema(description = "经度")
private String lgtd;
@Schema(description = "纬度")
private String lttd;
@Schema(description = "监测方式")
private Integer mway;
@Schema(description = "垂向水温类型:1=浮动式 2=固定式")
private Integer wtDeviceType;
@Schema(description = "所属流域")
private String hbrvcd;
@Schema(description = "站点排序")
private Integer orderIndex;
@Schema(description = "基地编码")
private String baseId;
@Schema(description = "基地排序")
private Integer baseStepSort;
@Schema(description = "站点排序")
private Integer siteStepSort;
@Schema(description = "范围内是否有日数据")
private Integer sort;
}

View File

@ -2,6 +2,7 @@ package com.yfd.platform.env.wt.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.env.wt.entity.vo.RstcdTreeInfoVo;
import com.yfd.platform.env.wt.entity.vo.WbsbVo; import com.yfd.platform.env.wt.entity.vo.WbsbVo;
import com.yfd.platform.env.wt.entity.vo.WtrvVo; import com.yfd.platform.env.wt.entity.vo.WtrvVo;
@ -20,4 +21,6 @@ public interface SdWtMonitorService {
WtrvVo getFlagByStcd(String stcd); WtrvVo getFlagByStcd(String stcd);
DataSourceResult<WbsbVo> getWbsbList(DataSourceRequest dataSourceRequest); DataSourceResult<WbsbVo> getWbsbList(DataSourceRequest dataSourceRequest);
List<RstcdTreeInfoVo> getWtvtDefaultTreeStcd(DataSourceRequest dataSourceRequest);
} }

View File

@ -4,11 +4,13 @@ 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.*; import com.yfd.platform.common.*;
import com.yfd.platform.env.wt.entity.vo.FishSpawnVo; import com.yfd.platform.env.wt.entity.vo.FishSpawnVo;
import com.yfd.platform.env.wt.entity.vo.SdWtMonitorCountVO; import com.yfd.platform.env.wt.entity.vo.RstcdTreeInfoVo;
import com.yfd.platform.env.wt.entity.vo.SdWtBaseInfoVO; import com.yfd.platform.env.wt.entity.vo.SdWtBaseInfoVO;
import com.yfd.platform.env.wt.entity.vo.SdWtMonitorCountVO;
import com.yfd.platform.env.wt.entity.vo.WbsbVo; import com.yfd.platform.env.wt.entity.vo.WbsbVo;
import com.yfd.platform.env.wt.entity.vo.WtrvVo;
import com.yfd.platform.env.wt.entity.vo.WtFishVo; import com.yfd.platform.env.wt.entity.vo.WtFishVo;
import com.yfd.platform.env.wt.entity.vo.WtTreeStcdVo;
import com.yfd.platform.env.wt.entity.vo.WtrvVo;
import com.yfd.platform.env.wt.mapper.SdWtMonitorMapper; import com.yfd.platform.env.wt.mapper.SdWtMonitorMapper;
import com.yfd.platform.env.wt.service.SdWtMonitorService; import com.yfd.platform.env.wt.service.SdWtMonitorService;
import com.yfd.platform.utils.QgcQueryWrapperUtil; import com.yfd.platform.utils.QgcQueryWrapperUtil;
@ -593,6 +595,282 @@ public class SdWtMonitorServiceImpl implements SdWtMonitorService {
return result; return result;
} }
@Override
public List<RstcdTreeInfoVo> getWtvtDefaultTreeStcd(DataSourceRequest dataSourceRequest) {
List<WtTreeStcdVo> stationList = queryWtvtDefaultStations(dataSourceRequest);
return buildWtvtRstcdTree(stationList);
}
private List<WtTreeStcdVo> queryWtvtDefaultStations(DataSourceRequest dataSourceRequest) {
DataSourceLoadOptionsBase loadOptions = dataSourceRequest == null ? null : dataSourceRequest.toDevRequest();
String tm = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "tm");
String mway = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "mway");
String baseId = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "baseId");
String rstcd = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "rstcd");
String year = loadOptions == null ? null : QgcQueryWrapperUtil.getFilterFieldValue(loadOptions, "year");
Map<String, Object> paramMap = new HashMap<>();
String sql;
if (StrUtil.isNotBlank(year)) {
paramMap.put("year", year);
if (StrUtil.isNotBlank(mway)) {
paramMap.put("mway", mway);
}
if (StrUtil.isNotBlank(baseId)) {
paramMap.put("baseId", baseId);
}
if (StrUtil.isNotBlank(rstcd)) {
paramMap.put("rstcd", rstcd);
}
sql = buildWtvtDefaultYearSql(paramMap);
} else {
List<String> tmRange = parseTmRange(tm);
if (tmRange.size() == 2) {
paramMap.put("startTime", tmRange.get(0));
paramMap.put("endTime", tmRange.get(1));
}
if (StrUtil.isNotBlank(mway)) {
paramMap.put("mway", mway);
}
if (StrUtil.isNotBlank(baseId)) {
paramMap.put("baseId", baseId);
}
sql = buildWtvtDefaultRangeSql(paramMap);
}
return microservicDynamicSQLMapper.getAllListWithResultType(sql, paramMap, WtTreeStcdVo.class);
}
private String buildWtvtDefaultYearSql(Map<String, Object> paramMap) {
StringBuilder sql = new StringBuilder();
sql.append("SELECT DISTINCT ")
.append("wt.STCD AS stcd, ")
.append("wt.STNM AS stnm, ")
.append("NVL(rstSort.SORT, eng.ORDER_INDEX) AS rstcdStepSort, ")
.append("wt.RSTCD AS rstcd, ")
.append("eng.ENNM AS ennm, ")
.append("TO_CHAR(wt.LGTD) AS lgtd, ")
.append("TO_CHAR(wt.LTTD) AS lttd, ")
.append("wt.MWAY AS mway, ")
.append("wt.WT_DEVICE_TYPE AS wtDeviceType, ")
.append("eng.HBRVCD AS hbrvcd, ")
.append("wt.ORDER_INDEX AS orderIndex, ")
.append("eng.BASE_ID AS baseId, ")
.append("hb.ORDER_INDEX AS baseStepSort, ")
.append("NVL(siteSort.SORT, wt.ORDER_INDEX) AS siteStepSort, ")
.append("1 AS sort ")
.append("FROM SD_WT_B_H wt ")
.append("INNER JOIN SD_WTVTDRTP_S drtp ON drtp.STCD = wt.STCD ")
.append("LEFT JOIN SD_ENGINFO_B_H eng ON eng.STCD = wt.RSTCD ")
.append("LEFT JOIN SD_HYDROBASE hb ON hb.BASEID = eng.BASE_ID AND NVL(hb.IS_DELETED, 0) = 0 ")
.append("LEFT JOIN (")
.append(" SELECT det.STCD, det.SORT, along.RVCD ")
.append(" FROM MS_ALONGDET_B det ")
.append(" INNER JOIN MS_ALONG_B along ON along.ID = det.ALONG_ID ")
.append(" WHERE NVL(det.IS_DELETED, 0) = 0 ")
.append(" AND NVL(along.IS_DELETED, 0) = 0 ")
.append(" AND along.CODE = 'common'")
.append(") rstSort ON rstSort.STCD = wt.RSTCD AND rstSort.RVCD = eng.HBRVCD ")
.append("LEFT JOIN (")
.append(" SELECT det.STCD, det.SORT, along.RVCD ")
.append(" FROM MS_ALONGDET_B det ")
.append(" INNER JOIN MS_ALONG_B along ON along.ID = det.ALONG_ID ")
.append(" WHERE NVL(det.IS_DELETED, 0) = 0 ")
.append(" AND NVL(along.IS_DELETED, 0) = 0 ")
.append(" AND along.CODE = 'common'")
.append(") siteSort ON siteSort.STCD = wt.STCD AND siteSort.RVCD = eng.HBRVCD ")
.append("WHERE NVL(wt.IS_DELETED, 0) = 0 ")
.append(" AND wt.STTP = 'WTVT' ")
.append(" AND NVL(wt.USFL, 0) = 1 ")
.append(" AND NVL(drtp.IS_DELETED, 0) = 0 ")
.append(" AND drtp.DRTP = 'YEAR' ")
.append(" AND drtp.YEAR = #{map.year} ")
.append(" AND drtp.WTHG IS NOT NULL ")
.append(" AND drtp.VWT IS NOT NULL ");
if (paramMap.containsKey("mway")) {
sql.append(" AND wt.MWAY = #{map.mway} ");
}
if (paramMap.containsKey("baseId")) {
sql.append(" AND eng.BASE_ID = #{map.baseId} ");
}
if (paramMap.containsKey("rstcd")) {
sql.append(" AND wt.RSTCD = #{map.rstcd} ");
}
sql.append("ORDER BY NVL(hb.ORDER_INDEX, 999999) ASC, ")
.append("NVL(NVL(rstSort.SORT, eng.ORDER_INDEX), 999999) ASC, ")
.append("NVL(NVL(siteSort.SORT, wt.ORDER_INDEX), 999999) ASC");
return sql.toString();
}
private String buildWtvtDefaultRangeSql(Map<String, Object> paramMap) {
StringBuilder sql = new StringBuilder();
sql.append("SELECT * FROM (")
.append("SELECT ")
.append("wt.STCD AS stcd, ")
.append("wt.STNM AS stnm, ")
.append("NVL(rstSort.SORT, eng.ORDER_INDEX) AS rstcdStepSort, ")
.append("wt.RSTCD AS rstcd, ")
.append("eng.ENNM AS ennm, ")
.append("TO_CHAR(wt.LGTD) AS lgtd, ")
.append("TO_CHAR(wt.LTTD) AS lttd, ")
.append("wt.MWAY AS mway, ")
.append("wt.WT_DEVICE_TYPE AS wtDeviceType, ")
.append("eng.HBRVCD AS hbrvcd, ")
.append("wt.ORDER_INDEX AS orderIndex, ")
.append("eng.BASE_ID AS baseId, ")
.append("hb.ORDER_INDEX AS baseStepSort, ")
.append("NVL(siteSort.SORT, wt.ORDER_INDEX) AS siteStepSort, ")
.append("CASE WHEN ");
if (paramMap.containsKey("startTime") && paramMap.containsKey("endTime")) {
sql.append("EXISTS (")
.append("SELECT 1 FROM SD_WTVTDAY_S dayData ")
.append("WHERE dayData.STCD = wt.STCD ")
.append(" AND NVL(dayData.IS_DELETED, 0) = 0 ")
.append(" AND dayData.DT >= TO_DATE(#{map.startTime}, 'YYYY-MM-DD HH24:MI:SS') ")
.append(" AND dayData.DT <= TO_DATE(#{map.endTime}, 'YYYY-MM-DD HH24:MI:SS') ")
.append(" AND dayData.WTHG IS NOT NULL ")
.append(" AND dayData.VWT IS NOT NULL")
.append(") ");
} else {
sql.append("1 = 0 ");
}
sql.append("THEN 1 ELSE -1 END AS sort ")
.append("FROM SD_WT_B_H wt ")
.append("LEFT JOIN SD_ENGINFO_B_H eng ON eng.STCD = wt.RSTCD ")
.append("LEFT JOIN SD_HYDROBASE hb ON hb.BASEID = eng.BASE_ID AND NVL(hb.IS_DELETED, 0) = 0 ")
.append("LEFT JOIN (")
.append(" SELECT det.STCD, det.SORT, along.RVCD ")
.append(" FROM MS_ALONGDET_B det ")
.append(" INNER JOIN MS_ALONG_B along ON along.ID = det.ALONG_ID ")
.append(" WHERE NVL(det.IS_DELETED, 0) = 0 ")
.append(" AND NVL(along.IS_DELETED, 0) = 0 ")
.append(" AND along.CODE = 'common'")
.append(") rstSort ON rstSort.STCD = wt.RSTCD AND rstSort.RVCD = eng.HBRVCD ")
.append("LEFT JOIN (")
.append(" SELECT det.STCD, det.SORT, along.RVCD ")
.append(" FROM MS_ALONGDET_B det ")
.append(" INNER JOIN MS_ALONG_B along ON along.ID = det.ALONG_ID ")
.append(" WHERE NVL(det.IS_DELETED, 0) = 0 ")
.append(" AND NVL(along.IS_DELETED, 0) = 0 ")
.append(" AND along.CODE = 'common'")
.append(") siteSort ON siteSort.STCD = wt.STCD AND siteSort.RVCD = eng.HBRVCD ")
.append("WHERE NVL(wt.IS_DELETED, 0) = 0 ")
.append(" AND wt.STTP = 'WTVT' ")
.append(" AND NVL(wt.USFL, 0) = 1 ")
.append(" AND EXISTS (")
.append(" SELECT 1 FROM SD_WTVTDRTP_S yearData ")
.append(" WHERE yearData.STCD = wt.STCD ")
.append(" AND NVL(yearData.IS_DELETED, 0) = 0 ")
.append(" AND yearData.DRTP = 'YEAR' ")
.append(" AND yearData.WTHG IS NOT NULL ")
.append(" AND yearData.VWT IS NOT NULL")
.append(" ) ");
if (paramMap.containsKey("mway")) {
sql.append(" AND wt.MWAY = #{map.mway} ");
}
if (paramMap.containsKey("baseId")) {
sql.append(" AND eng.BASE_ID = #{map.baseId} ");
}
sql.append(") ")
.append("ORDER BY NVL(baseStepSort, 999999) ASC, ")
.append("NVL(rstcdStepSort, 999999) ASC, ")
.append("NVL(siteStepSort, 999999) ASC, ")
.append("sort DESC");
return sql.toString();
}
private List<String> parseTmRange(String tm) {
if (StrUtil.isBlank(tm)) {
return Collections.emptyList();
}
String[] split = tm.split(",");
List<String> result = new ArrayList<>();
for (String item : split) {
if (StrUtil.isNotBlank(item)) {
result.add(item.trim());
}
}
return result;
}
private List<RstcdTreeInfoVo> buildWtvtRstcdTree(List<WtTreeStcdVo> stationList) {
if (stationList == null || stationList.isEmpty()) {
return new ArrayList<>();
}
LinkedHashMap<String, RstcdTreeInfoVo> treeMap = new LinkedHashMap<>();
List<WtTreeStcdVo> otherStations = new ArrayList<>();
for (WtTreeStcdVo station : stationList) {
List<String> rstcdCodes = splitRstcdCodes(station.getRstcd());
if (rstcdCodes.isEmpty()) {
otherStations.add(station);
continue;
}
for (String rstcdCode : rstcdCodes) {
RstcdTreeInfoVo treeInfo = treeMap.computeIfAbsent(rstcdCode, key -> {
RstcdTreeInfoVo vo = new RstcdTreeInfoVo();
vo.setRstcd(key);
vo.setEnnm(station.getEnnm());
return vo;
});
if (StrUtil.isBlank(treeInfo.getEnnm()) && StrUtil.isNotBlank(station.getEnnm())) {
treeInfo.setEnnm(station.getEnnm());
}
boolean exists = treeInfo.getStcdVo().stream()
.anyMatch(item -> StrUtil.equals(item.getStcd(), station.getStcd()));
if (!exists) {
treeInfo.getStcdVo().add(station);
}
}
}
fillMissingTreeEnnm(treeMap);
List<RstcdTreeInfoVo> result = new ArrayList<>(treeMap.values());
if (!otherStations.isEmpty()) {
RstcdTreeInfoVo other = new RstcdTreeInfoVo();
other.setRstcd("other");
other.setEnnm("其它");
other.setStcdVo(otherStations);
result.add(other);
}
return result;
}
private List<String> splitRstcdCodes(String rstcd) {
if (StrUtil.isBlank(rstcd)) {
return Collections.emptyList();
}
List<String> result = new ArrayList<>();
for (String item : rstcd.split(",")) {
if (StrUtil.isNotBlank(item)) {
result.add(item.trim());
}
}
return result;
}
private void fillMissingTreeEnnm(LinkedHashMap<String, RstcdTreeInfoVo> treeMap) {
List<String> missingCodes = treeMap.values().stream()
.filter(item -> StrUtil.isNotBlank(item.getRstcd()) && StrUtil.isBlank(item.getEnnm()))
.map(RstcdTreeInfoVo::getRstcd)
.distinct()
.collect(Collectors.toList());
if (missingCodes.isEmpty()) {
return;
}
String inSql = missingCodes.stream()
.map(code -> "'" + code.replace("'", "''") + "'")
.collect(Collectors.joining(","));
String sql = "SELECT STCD AS stcd, ENNM AS ennm FROM SD_ENGINFO_B_H " +
"WHERE NVL(IS_DELETED, 0) = 0 AND STCD IN (" + inSql + ")";
List<WtTreeNodeEnnmRow> rowList = microservicDynamicSQLMapper.getAllListWithResultType(sql, new HashMap<>(), WtTreeNodeEnnmRow.class);
Map<String, String> ennmMap = rowList.stream()
.filter(item -> StrUtil.isNotBlank(item.getStcd()))
.collect(Collectors.toMap(WtTreeNodeEnnmRow::getStcd, WtTreeNodeEnnmRow::getEnnm, (left, right) -> left));
for (Map.Entry<String, RstcdTreeInfoVo> entry : treeMap.entrySet()) {
if (StrUtil.isBlank(entry.getValue().getEnnm())) {
entry.getValue().setEnnm(ennmMap.get(entry.getKey()));
}
}
}
private Page<?> buildPage(DataSourceLoadOptionsBase loadOptions) { private Page<?> buildPage(DataSourceLoadOptionsBase loadOptions) {
PageInfo pageInfo = QgcQueryWrapperUtil.getPageInfo(loadOptions); PageInfo pageInfo = QgcQueryWrapperUtil.getPageInfo(loadOptions);
if (Boolean.TRUE.equals(pageInfo.getHasPageInfo())) { if (Boolean.TRUE.equals(pageInfo.getHasPageInfo())) {
@ -846,4 +1124,10 @@ public class SdWtMonitorServiceImpl implements SdWtMonitorService {
private String vwt; private String vwt;
} }
@Data
private static class WtTreeNodeEnnmRow {
private String stcd;
private String ennm;
}
} }