ids = expiredTasks.stream().map(ImportTask::getId).toList();
+ return this.removeByIds(ids);
+ }
+}
\ No newline at end of file
diff --git a/backend/src/main/java/com/yfd/platform/data/service/impl/SysUserDataScopeServiceImpl.java b/backend/src/main/java/com/yfd/platform/data/service/impl/SysUserDataScopeServiceImpl.java
index 3dd6828..7492688 100644
--- a/backend/src/main/java/com/yfd/platform/data/service/impl/SysUserDataScopeServiceImpl.java
+++ b/backend/src/main/java/com/yfd/platform/data/service/impl/SysUserDataScopeServiceImpl.java
@@ -1,13 +1,29 @@
package com.yfd.platform.data.service.impl;
+import cn.hutool.core.collection.CollUtil;
+import cn.hutool.core.util.StrUtil;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yfd.platform.data.domain.SysUserDataScope;
+import com.yfd.platform.data.domain.bo.EditUserDataScopeBo;
+import com.yfd.platform.data.domain.vo.SysUserDataScopeVO;
import com.yfd.platform.data.mapper.SysUserDataScopeMapper;
import com.yfd.platform.data.service.ISysUserDataScopeService;
+import com.yfd.platform.env.domain.SdEngInfoBH;
+import com.yfd.platform.env.domain.SdHycdDic;
+import com.yfd.platform.env.domain.SdHydrobase;
+import com.yfd.platform.env.domain.SdRvcdDic;
+import com.yfd.platform.env.mapper.SdEngInfoBHMapper;
+import com.yfd.platform.env.mapper.SdHycdDicMapper;
+import com.yfd.platform.env.mapper.SdHydrobaseMapper;
+import com.yfd.platform.env.mapper.SdRvcdDicMapper;
+import jakarta.annotation.Resource;
+import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
-import java.util.List;
+import java.util.*;
+import java.util.stream.Collectors;
/**
*
@@ -16,6 +32,17 @@ import java.util.List;
*/
@Service
public class SysUserDataScopeServiceImpl extends ServiceImpl implements ISysUserDataScopeService {
+ @Resource
+ private SdRvcdDicMapper rvcdDicMapper;
+
+ @Resource
+ private SdHydrobaseMapper hydrobaseMapper;
+
+ @Resource
+ private SdHycdDicMapper hycdDicMapper;
+
+ @Resource
+ private SdEngInfoBHMapper engInfoBHMapper;
@Override
public Page queryPageList(Page page, String userId, String orgType, String orgId, Integer status) {
@@ -73,4 +100,174 @@ public class SysUserDataScopeServiceImpl extends ServiceImpl getValidPermissionsWithOrgName(String userId) {
+ // 1. 查询用户的有效权限
+ List permissions = this.getValidPermissions(userId);
+
+ if (CollUtil.isEmpty(permissions)) {
+ return Collections.emptyList();
+ }
+
+ // 2. 按 orgType 分组
+ Map> groupedByType = permissions.stream()
+ .collect(Collectors.groupingBy(SysUserDataScope::getOrgType));
+
+ // 3. 批量查询各类资源的名称
+ Map orgNameMap = new HashMap<>();
+
+ // 3.1 查询流域名称 (BASIN)
+ if (groupedByType.containsKey("BASIN")) {
+ Set rvcds = groupedByType.get("BASIN").stream()
+ .map(SysUserDataScope::getOrgId)
+ .filter(StrUtil::isNotBlank)
+ .collect(Collectors.toSet());
+
+ if (CollUtil.isNotEmpty(rvcds)) {
+ List basins = rvcdDicMapper.selectBatchIds(rvcds);
+ basins.forEach(basin -> orgNameMap.put(basin.getRvcd(), basin.getRvnm()));
+ }
+ }
+
+ // 3.2 查询基地名称 (BASE)
+ if (groupedByType.containsKey("BASE")) {
+ Set baseIds = groupedByType.get("BASE").stream()
+ .map(SysUserDataScope::getOrgId)
+ .filter(StrUtil::isNotBlank)
+ .collect(Collectors.toSet());
+
+ if (CollUtil.isNotEmpty(baseIds)) {
+ List bases = hydrobaseMapper.selectBatchIds(baseIds);
+ bases.forEach(base -> orgNameMap.put(base.getBaseid(), base.getBasename()));
+ }
+ }
+
+ // 3.3 查询公司名称 (COMPANY)
+ if (groupedByType.containsKey("COMPANY")) {
+ Set hycds = groupedByType.get("COMPANY").stream()
+ .map(SysUserDataScope::getOrgId)
+ .filter(StrUtil::isNotBlank)
+ .collect(Collectors.toSet());
+
+ if (CollUtil.isNotEmpty(hycds)) {
+ List companies = hycdDicMapper.selectBatchIds(hycds);
+ companies.forEach(company -> orgNameMap.put(company.getHycd(), company.getHynm()));
+ }
+ }
+
+ // 3.4 查询电站名称 (STATION)
+ if (groupedByType.containsKey("STATION")) {
+ Set stcds = groupedByType.get("STATION").stream()
+ .map(SysUserDataScope::getOrgId)
+ .filter(StrUtil::isNotBlank)
+ .collect(Collectors.toSet());
+
+ if (CollUtil.isNotEmpty(stcds)) {
+ List stations = engInfoBHMapper.selectBatchIds(stcds);
+ stations.forEach(station -> orgNameMap.put(station.getStcd(), station.getEnnm()));
+ }
+ }
+
+ // 4. 组装 VO 对象
+ List voList = new ArrayList<>();
+ for (SysUserDataScope permission : permissions) {
+ SysUserDataScopeVO vo = new SysUserDataScopeVO();
+ BeanUtils.copyProperties(permission, vo);
+
+ // 设置资源名称
+ String orgName = orgNameMap.get(permission.getOrgId());
+ vo.setOrgName(StrUtil.blankToDefault(orgName, "未知"));
+
+ voList.add(vo);
+ }
+
+ return voList;
+ }
+
+ @Override
+ public boolean batchAddDataScope(EditUserDataScopeBo editUserDataScopeBo) {
+ List dataScopeList = editUserDataScopeBo.getDataScopeList();
+ if (CollUtil.isEmpty(dataScopeList)) {
+ String userId = editUserDataScopeBo.getUserId();
+ // 删除旧数据
+ this.remove(new LambdaQueryWrapper().eq(SysUserDataScope::getUserId, userId));
+ return true;
+ }
+ // 1. 去重:基于 userId + orgType + orgId 去除传入列表中的重复数据
+ List uniqueList = dataScopeList.stream()
+ .collect(Collectors.toMap(
+ scope -> buildUniqueKey(scope.getUserId(), scope.getOrgType(), scope.getOrgId()),
+ scope -> scope,
+ (existing, replacement) -> replacement // 如果有重复,保留后者
+ ))
+ .values()
+ .stream()
+ .collect(Collectors.toList());
+
+ // 2. 提取所有需要处理的唯一键
+ Set targetKeys = uniqueList.stream()
+ .map(scope -> buildUniqueKey(scope.getUserId(), scope.getOrgType(), scope.getOrgId()))
+ .collect(Collectors.toSet());
+
+ // 3. 查询数据库中已存在的记录
+ List existingRecords = this.lambdaQuery()
+ .in(SysUserDataScope::getUserId,
+ uniqueList.stream().map(SysUserDataScope::getUserId).collect(Collectors.toSet()))
+ .list();
+
+ // 4. 找出需要删除的记录(数据库中存在但新列表中不存在的)
+ Set existingKeys = existingRecords.stream()
+ .map(record -> buildUniqueKey(record.getUserId(), record.getOrgType(), record.getOrgId()))
+ .collect(Collectors.toSet());
+
+ List idsToDelete = existingRecords.stream()
+ .filter(record -> !targetKeys.contains(
+ buildUniqueKey(record.getUserId(), record.getOrgType(), record.getOrgId())
+ ))
+ .map(SysUserDataScope::getId)
+ .collect(Collectors.toList());
+
+ // 5. 找出需要更新的记录(数据库和新列表中都存在的)
+ List toUpdate = uniqueList.stream()
+ .filter(scope -> existingKeys.contains(
+ buildUniqueKey(scope.getUserId(), scope.getOrgType(), scope.getOrgId())
+ ))
+ .peek(scope -> {
+ // 设置已存在记录的ID
+ existingRecords.stream()
+ .filter(existing -> buildUniqueKey(existing.getUserId(), existing.getOrgType(), existing.getOrgId())
+ .equals(buildUniqueKey(scope.getUserId(), scope.getOrgType(), scope.getOrgId())))
+ .findFirst()
+ .ifPresent(existing -> scope.setId(existing.getId()));
+ })
+ .collect(Collectors.toList());
+
+ // 6. 找出需要新增的记录(数据库中不存在的)
+ List toInsert = uniqueList.stream()
+ .filter(scope -> !existingKeys.contains(
+ buildUniqueKey(scope.getUserId(), scope.getOrgType(), scope.getOrgId())
+ ))
+ .collect(Collectors.toList());
+
+ // 7. 执行删除操作
+ if (CollUtil.isNotEmpty(idsToDelete)) {
+ this.removeByIds(idsToDelete);
+ }
+
+ // 8. 执行批量新增和更新
+ boolean insertResult = CollUtil.isEmpty(toInsert) || this.saveBatch(toInsert);
+ boolean updateResult = CollUtil.isEmpty(toUpdate) || this.updateBatchById(toUpdate);
+ return insertResult && updateResult;
+ }
+
+ /**
+ * 构建唯一键(userId + orgType + orgId)
+ */
+ private String buildUniqueKey(String userId, String orgType, String orgId) {
+ return String.format("%s_%s_%s",
+ StrUtil.blankToDefault(userId, ""),
+ StrUtil.blankToDefault(orgType, ""),
+ StrUtil.blankToDefault(orgId, ""));
+ }
}
diff --git a/backend/src/main/java/com/yfd/platform/env/controller/TreeStructureController.java b/backend/src/main/java/com/yfd/platform/env/controller/TreeStructureController.java
index 4286e1d..f1c4b4b 100644
--- a/backend/src/main/java/com/yfd/platform/env/controller/TreeStructureController.java
+++ b/backend/src/main/java/com/yfd/platform/env/controller/TreeStructureController.java
@@ -10,6 +10,8 @@ import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import jakarta.annotation.Resource;
+
+import java.util.ArrayList;
import java.util.List;
import java.util.Map;
@@ -26,20 +28,45 @@ public class TreeStructureController {
@Resource
private ITreeStructureService treeStructureService;
+ @GetMapping("/rvcdEng")
+ @Operation(summary = "获取流域-电站树形结构")
+ public ResponseResult getRvcdEngTree(
+ @RequestParam(required = false) String rvcd,
+ @RequestParam(required = false) String engName) {
+ List