chenxiaofei 5 tuntia sitten
vanhempi
commit
7d38f6a74c

+ 8 - 0
sckw-modules-api/sckw-contract-api/src/main/java/com/sckw/contract/api/RemoteContractService.java

@@ -208,5 +208,13 @@ public interface RemoteContractService {
      */
     List<Long> queryProxyGoodsIds(Long entId, Long proxyEntId);
 
+    /**
+     * 根据代理商企业ID查询代理合同对应的供应商企业ID集合。
+     *
+     * @param proxyEntId 代理商企业ID
+     * @return 供应商企业ID集合
+     */
+    List<Long> querySupplyEntIdsByProxyId(Long proxyEntId);
+
     List<TradeEntInfoResVo> queryPrepaidTradeEntIds(TradeEntListQueryFeignDto queryFeignDto);
 }

+ 26 - 0
sckw-modules/sckw-contract/src/main/java/com/sckw/contract/dubbo/RemoteContractServiceImpl.java

@@ -821,6 +821,32 @@ public class RemoteContractServiceImpl implements RemoteContractService {
         return proxyEntIds;
     }
 
+    /**
+     * 根据代理商企业ID查询代理合同对应的供应商企业ID集合。
+     *
+     * @param proxyEntId 代理商企业ID
+     * @return 供应商企业ID列表,若未找到则返回空列表
+     */
+    @Override
+    public List<Long> querySupplyEntIdsByProxyId(Long proxyEntId) {
+        if (Objects.isNull(proxyEntId)) {
+            log.warn("查询代理合同供应商企业ID失败,代理商企业ID为空");
+            return Collections.emptyList();
+        }
+        List<KwcContractProxy> proxyContracts = kwcContractProxyRepository.queryByProxyId(proxyEntId);
+        if (CollectionUtils.isEmpty(proxyContracts)) {
+            log.debug("代理商[{}]未找到任何关联的代理合同", proxyEntId);
+            return Collections.emptyList();
+        }
+        List<Long> supplyEntIds = proxyContracts.stream()
+                .map(KwcContractProxy::getSupplyId)
+                .filter(Objects::nonNull)
+                .distinct()
+                .collect(Collectors.toList());
+        log.info("成功查询到代理商[{}]对应的{}个供应商企业ID", proxyEntId, supplyEntIds.size());
+        return supplyEntIds;
+    }
+
     @Override
     public List<ContractVo> tradeList() {
         List<Long> ids = new ArrayList<>();

+ 12 - 0
sckw-modules/sckw-contract/src/main/java/com/sckw/contract/repository/KwcContractProxyRepository.java

@@ -71,4 +71,16 @@ public class KwcContractProxyRepository extends ServiceImpl<KwcContractProxyMapp
                 .eq(KwcContractProxy::getDelFlag, 0)
                 .eq(KwcContractProxy::getSupplyId, supplyId));
     }
+
+    /**
+     * 根据代理商企业ID查询代理合同。
+     *
+     * @param proxyId 代理商企业ID
+     * @return 代理合同集合
+     */
+    public List<KwcContractProxy> queryByProxyId(Long proxyId) {
+        return list(Wrappers.<KwcContractProxy>lambdaQuery()
+                .eq(KwcContractProxy::getDelFlag, 0)
+                .eq(KwcContractProxy::getProxyId, proxyId));
+    }
 }

+ 1 - 5
sckw-modules/sckw-product/src/main/java/com/sckw/product/model/vo/req/GoodsInfoReq.java

@@ -23,11 +23,7 @@ public class GoodsInfoReq implements Serializable {
      */
     @Schema(description = "企业id")
     private String entId;
-    /**
-     * 代理商id
-     */
-    @Schema(description = "代理商id")
-    private String proxyEntId;
+
     /**
      * 商品名称
      */

+ 1 - 37
sckw-modules/sckw-product/src/main/java/com/sckw/product/service/KwpGoodsService.java

@@ -1490,10 +1490,8 @@ public class KwpGoodsService {
 
     public GoodsInfoResp getGoods(GoodsInfoReq req) {
         log.info("查询商品信息,请求参数 :{}", JSON.toJSONString(req));
-        //查询上商品信息
         Long entId = parseLongParam(req.getEntId(), "企业id");
-        Long proxyEntId = parseLongParam(req.getProxyEntId(), "代理商id");
-        List<KwpGoods> goods = queryGoodsInfoList(req, entId, proxyEntId);
+        List<KwpGoods> goods = kwpGoodsRepository.queryByEntIdAndGoodsName(entId, req.getGoodsName());
         log.info("查询商品信息,返回条数 :{}", goods.size());
         if (org.apache.commons.collections4.CollectionUtils.isEmpty(goods)) {
             return new GoodsInfoResp();
@@ -1508,40 +1506,6 @@ public class KwpGoodsService {
         return goodsInfoResp;
     }
 
-    /**
-     * 查询商品信息列表。企业id和代理商id同时传入时,按代理合同商品限定商品范围;代理商id未传入时保持原有查询逻辑。
-     *
-     * @param req        查询商品请求参数
-     * @param entId      企业id
-     * @param proxyEntId 代理商id
-     * @return 商品信息列表
-     */
-    private List<KwpGoods> queryGoodsInfoList(GoodsInfoReq req, Long entId, Long proxyEntId) {
-        if (!isProxyGoodsQuery(req)) {
-            log.info("查询商品信息,请求参数 :{}", JSON.toJSONString(req));
-            return kwpGoodsRepository.queryByEntIdAndGoodsName(entId, req.getGoodsName());
-        }
-        List<Long> proxyGoodsIds = remoteContractService.queryProxyGoodsIds(entId, proxyEntId);
-        log.info("查询代理商品信息,企业id :{}, 代理商id :{},条数:{}", entId, proxyEntId, proxyGoodsIds.size());
-        if (CollUtil.isEmpty(proxyGoodsIds)) {
-            log.info("查询代理商品信息为空");
-            return Collections.emptyList();
-        }
-        return kwpGoodsRepository.queryByIdsAndGoodsName(proxyGoodsIds, req.getGoodsName());
-    }
-
-    /**
-     * 判断是否按代理合同商品查询。只有企业id与代理商id同时存在时才切换新逻辑,避免影响原有调用方。
-     *
-     * @param req 查询商品请求参数
-     * @return true-按代理合同商品查询;false-按原有企业商品查询
-     */
-    static boolean isProxyGoodsQuery(GoodsInfoReq req) {
-        return Objects.nonNull(req)
-                && StringUtils.isNotBlank(req.getEntId())
-                && StringUtils.isNotBlank(req.getProxyEntId());
-    }
-
     /**
      * 安全转换Long参数,避免非法字符串导致系统异常。
      *

+ 0 - 34
sckw-modules/sckw-product/src/test/java/com/sckw/product/service/KwpGoodsServiceTest.java

@@ -1,34 +0,0 @@
-package com.sckw.product.service;
-
-import com.sckw.product.model.vo.req.GoodsInfoReq;
-import org.junit.Assert;
-import org.junit.Test;
-
-/**
- * 商品服务单元测试。
- */
-public class KwpGoodsServiceTest {
-
-    /**
-     * 企业id和代理商id同时存在时,应按代理合同商品查询。
-     */
-    @Test
-    public void shouldUseProxyGoodsQueryWhenEntIdAndProxyEntIdExist() {
-        GoodsInfoReq req = new GoodsInfoReq();
-        req.setEntId("1001");
-        req.setProxyEntId("2001");
-
-        Assert.assertTrue(KwpGoodsService.isProxyGoodsQuery(req));
-    }
-
-    /**
-     * 代理商id为空时,应保持原有企业商品查询逻辑。
-     */
-    @Test
-    public void shouldKeepOriginalGoodsQueryWhenProxyEntIdMissing() {
-        GoodsInfoReq req = new GoodsInfoReq();
-        req.setEntId("1001");
-
-        Assert.assertFalse(KwpGoodsService.isProxyGoodsQuery(req));
-    }
-}

+ 6 - 0
sckw-modules/sckw-system/src/main/java/com/sckw/system/model/vo/req/EntInfoReq.java

@@ -36,4 +36,10 @@ public class EntInfoReq implements Serializable {
      */
     @Schema(description = "企业名称")
     private String entName;
+
+    /**
+     * 代理商id(不为空时按代理合同查询对应供应商企业)
+     */
+    @Schema(description = "代理商id")
+    private String agentId;
 }

+ 55 - 0
sckw-modules/sckw-system/src/main/java/com/sckw/system/service/KwsEnterpriseService.java

@@ -11,6 +11,7 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.toolkit.Wrappers;
 import com.github.pagehelper.PageHelper;
 import com.github.pagehelper.PageInfo;
+import com.sckw.contract.api.RemoteContractService;
 import com.sckw.core.exception.BusinessException;
 import com.sckw.core.exception.SystemException;
 import com.sckw.core.model.base.BaseModel;
@@ -50,6 +51,7 @@ import jakarta.servlet.http.HttpServletRequest;
 import jakarta.servlet.http.HttpServletResponse;
 import lombok.RequiredArgsConstructor;
 import lombok.extern.slf4j.Slf4j;
+import org.apache.dubbo.config.annotation.DubboReference;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 import org.redisson.api.RSet;
@@ -125,6 +127,10 @@ public class KwsEnterpriseService {
     private KwsSpecialDao specialDao;
     @Autowired
     private RemoteBaseService remoteBaseService;
+
+    @DubboReference(version = "1.0.0", group = "design", check = false, timeout = 8000)
+    private RemoteContractService remoteContractService;
+
     private final KwsEntTypeRepository kwsEntTypeRepository;
     private final KwsEnterpriseRepository kwsEnterpriseRepository;
 
@@ -1551,16 +1557,22 @@ public class KwsEnterpriseService {
         if (req.getEntType().contains(req.getLoginEntType())) {
             //登录客户的企业类型和查询的类型是一直的说明只能查询自己和自己的下级
             //发起方的公司信息
+            log.info("发起方的公司信息登录客户=%s,发起方=%s,查询=%s", req.getEntId(), req.getLoginEntType(), req.getEntType());
             return getEntInfoResp(req);
         }
         //被邀请方的企业信息
         //根据类型查询企业id
+        log.info("被邀请方的企业信息登录客户=%s,发起方=%s,查询=%s", req.getEntId(), req.getLoginEntType(), req.getEntType());
         return getInfoResp(req);
     }
 
     @NotNull
     private EntInfoResp getInfoResp(EntInfoReq req) {
         EntInfoResp entInfoResp = buildEntInfoResp(req);
+        if (org.apache.commons.lang3.StringUtils.isNotBlank(req.getAgentId())) {
+            log.info("被邀请方按代理商查询供应商企业,agentId={}", req.getAgentId());
+            return getProxySupplyEntInfoResp(req, entInfoResp);
+        }
         List<KwsEntType> kwsEntTypes = kwsEntTypeRepository.queryByType(req.getEntType());
         if (CollectionUtils.isEmpty(kwsEntTypes)) {
             return entInfoResp;
@@ -1582,9 +1594,52 @@ public class KwsEnterpriseService {
         return entInfoResp;
     }
 
+    /**
+     * 按代理商id查询代理合同关联的供应商企业。
+     */
+    private EntInfoResp getProxySupplyEntInfoResp(EntInfoReq req, EntInfoResp entInfoResp) {
+        Long agentId = parseAgentId(req.getAgentId());
+        List<Long> supplyEntIds = remoteContractService.querySupplyEntIdsByProxyId(agentId);
+        log.info("按代理商查询供应商企业,agentId={}, supplyEntCount={}", agentId, supplyEntIds.size());
+        if (CollectionUtils.isEmpty(supplyEntIds)) {
+            return entInfoResp;
+        }
+        Set<Long> supplyEntIdSet = new HashSet<>(supplyEntIds);
+        List<KwsEntType> kwsEntTypes = kwsEntTypeRepository.queryByEntIdsAndType(supplyEntIdSet, req.getEntType());
+        if (CollectionUtils.isEmpty(kwsEntTypes)) {
+            return entInfoResp;
+        }
+        Set<Long> matchedEntIds = kwsEntTypes.stream().map(KwsEntType::getEntId).collect(Collectors.toSet());
+        List<KwsEnterprise> kwsEnterprises = kwsEnterpriseRepository.queryByEntIds(matchedEntIds, req.getEntName());
+        if (CollectionUtils.isEmpty(kwsEnterprises)) {
+            return entInfoResp;
+        }
+        List<EntInfoResp.EntInfo> entInfos = kwsEnterprises.stream().map(k -> {
+            EntInfoResp.EntInfo info = new EntInfoResp.EntInfo();
+            info.setEntId(String.valueOf(k.getId()));
+            info.setEntName(k.getFirmName());
+            return info;
+        }).collect(Collectors.toList());
+        entInfoResp.setEntInfos(entInfos);
+        return entInfoResp;
+    }
+
+    private Long parseAgentId(String agentId) {
+        try {
+            return Long.valueOf(agentId);
+        } catch (NumberFormatException e) {
+            log.warn("代理商id格式不正确,agentId={}", agentId, e);
+            throw new BusinessException("代理商id格式不正确");
+        }
+    }
+
     @NotNull
     private EntInfoResp getEntInfoResp(EntInfoReq req) {
         EntInfoResp entInfoResp = buildEntInfoResp(req);
+        if (org.apache.commons.lang3.StringUtils.isNotBlank(req.getAgentId())) {
+            log.info("发起方按代理商查询供应商企业,agentId={}", req.getAgentId());
+            return getProxySupplyEntInfoResp(req, entInfoResp);
+        }
         if (org.apache.commons.lang3.StringUtils.isBlank(req.getEntId())) {
             throw new BusinessException("企业id不能为空");
         }

+ 132 - 27
sckw-modules/sckw-system/src/main/java/com/sckw/system/service/KwsMenuService.java

@@ -138,29 +138,29 @@ public class KwsMenuService {
             throw new SystemException(HttpStatus.CRUD_FAIL_CODE, HttpStatus.INSERT_FAIL);
         }
 
-        List<FindEntListResVo> list = kwsEnterpriseDao.findList(new FindListReqVo());
-        if (CollectionUtils.isNotEmpty(list)) {
-            List<Long> entIds = list.stream().map(FindEntListResVo::getId).distinct().toList();
-            List<KwsMenuRights> kwsMenuRightsList = new ArrayList<>();
-            Date date = new Date();
-            for (Long entId : entIds) {
-                KwsMenuRights kwsMenuRights = new KwsMenuRights();
-                kwsMenuRights.setEntId(entId);
-                kwsMenuRights.setMenuId(menuId);
-                kwsMenuRights.setId(new IdWorker(1L).nextId());
-                kwsMenuRights.setDelFlag(Global.NO);
-                kwsMenuRights.setStatus(Global.NO);
-                kwsMenuRights.setCreateBy(LoginUserHolder.getUserId());
-                kwsMenuRights.setUpdateBy(LoginUserHolder.getUserId());
-                kwsMenuRights.setCreateTime(date);
-                kwsMenuRights.setUpdateTime(date);
-                kwsMenuRightsList.add(kwsMenuRights);
-            }
-
-            if (kwsMenuRightsDao.saveBatch(kwsMenuRightsList) < kwsMenuRightsList.size()) {
-                throw new SystemException(HttpStatus.CRUD_FAIL_CODE, HttpStatus.INSERT_FAIL);
-            }
-        }
+//        List<FindEntListResVo> list = kwsEnterpriseDao.findList(new FindListReqVo());
+//        if (CollectionUtils.isNotEmpty(list)) {
+//            List<Long> entIds = list.stream().map(FindEntListResVo::getId).distinct().toList();
+//            List<KwsMenuRights> kwsMenuRightsList = new ArrayList<>();
+//            Date date = new Date();
+//            for (Long entId : entIds) {
+//                KwsMenuRights kwsMenuRights = new KwsMenuRights();
+//                kwsMenuRights.setEntId(entId);
+//                kwsMenuRights.setMenuId(menuId);
+//                kwsMenuRights.setId(new IdWorker(1L).nextId());
+//                kwsMenuRights.setDelFlag(Global.NO);
+//                kwsMenuRights.setStatus(Global.NO);
+//                kwsMenuRights.setCreateBy(LoginUserHolder.getUserId());
+//                kwsMenuRights.setUpdateBy(LoginUserHolder.getUserId());
+//                kwsMenuRights.setCreateTime(date);
+//                kwsMenuRights.setUpdateTime(date);
+//                kwsMenuRightsList.add(kwsMenuRights);
+//            }
+//
+//            if (kwsMenuRightsDao.saveBatch(kwsMenuRightsList) < kwsMenuRightsList.size()) {
+//                throw new SystemException(HttpStatus.CRUD_FAIL_CODE, HttpStatus.INSERT_FAIL);
+//            }
+//        }
 
     }
 
@@ -665,10 +665,13 @@ public class KwsMenuService {
             finalList = menuList;
         }
         if (Objects.equals(LoginUserHolder.getSystemType(), SystemTypeEnum.COMPANY.getCode()) ) {
-//            if (Boolean.TRUE.equals(reqVo.getIncludeButton())) {
-//
-//            }
-            finalList = supplementButtons(finalList, findMenuTreePojo.getEntTypeList(),Integer.valueOf(reqVo.getClientType()));
+            if (needRightsBasedButtons(reqVo)) {
+                log.info("企业端 PC 且未指定菜单类型,按钮需基于 kws_menu_rights 权限查询");
+                finalList = supplementButtonsWithRights(finalList, findMenuTreePojo, Global.NUMERICAL_TWO);
+            } else {
+                log.info("企业端 PC 菜单类型,菜单权限查询");
+                finalList = supplementButtons(finalList, findMenuTreePojo.getEntTypeList(), Integer.valueOf(reqVo.getClientType()));
+            }
         }
 
 
@@ -747,6 +750,108 @@ public class KwsMenuService {
         findMenuTreePojo.setRoleIds(Collections.singletonList(LoginUserHolder.getCurrentRoleId()));
     }
 
+    /**
+     * 企业端 PC 且未指定菜单类型时,按钮需基于 kws_menu_rights 权限查询。
+     */
+    private boolean needRightsBasedButtons(FindMenuTreeReqVo reqVo) {
+        return reqVo.getType() == null
+                && org.apache.commons.lang3.StringUtils.equals(reqVo.getClientType(), String.valueOf(Global.NUMERICAL_TWO));
+    }
+
+    /**
+     * 基于菜单权限表补充按钮节点(企业端 PC 场景专用)。
+     * <p>
+     * 适用场景:{@link #findTree(FindMenuTreeReqVo)} 中企业端(systemType=2)、PC 端(clientType=2)、
+     * 且未指定菜单类型(type 为空)时调用,与 {@link #supplementButtons} 的区别在于:
+     * <ul>
+     *     <li>supplementButtons:直接从 kws_menu 查按钮,不做权限过滤</li>
+     *     <li>本方法:先查 kws_menu_rights 获取有权 menuId,再关联 kws_menu 查按钮</li>
+     * </ul>
+     * </p>
+     * <p>处理步骤:</p>
+     * <ol>
+     *     <li>从已有菜单列表中提取目录节点(type=1)作为按钮父级</li>
+     *     <li>按 roleIds / entId 查询 kws_menu_rights,得到有权限的 menuId 集合</li>
+     *     <li>在 kws_menu 中查询 type=2、clientType 匹配、parentId 属于目录且 id 在权限集合内的按钮</li>
+     *     <li>按 using_roles 过滤企业类型后,去重合并到菜单列表</li>
+     * </ol>
+     *
+     * @param menuList   已查询出的菜单列表(不含或已含部分按钮)
+     * @param pojo       查询条件,含 roleIds、entId、entTypeList
+     * @param clientType 客户端类型(企业端 PC 为 2)
+     * @return 合并按钮后的菜单列表
+     */
+    private List<KwsMenuResVo> supplementButtonsWithRights(List<KwsMenuResVo> menuList, FindMenuTreePojo pojo, Integer clientType) {
+        log.info("开始基于权限表补充按钮,clientType={}, entId={}, roleIds={}, 原菜单数={}",
+                clientType, pojo.getEntId(), pojo.getRoleIds(), menuList.size());
+
+        // 1. 提取目录节点 id,作为按钮的 parentId 查询范围
+        List<Long> menuTypeIds = menuList.stream()
+                .filter(m -> Objects.equals(m.getType(), MenuTypeEnum.DIRECTORY.getCode()))
+                .map(KwsMenuResVo::getId)
+                .toList();
+        if (CollectionUtils.isEmpty(menuTypeIds)) {
+            log.info("基于权限表补充按钮结束,未找到目录节点,跳过按钮查询");
+            return menuList;
+        }
+        log.debug("基于权限表补充按钮,目录节点数={}, directoryIds={}", menuTypeIds.size(), menuTypeIds);
+
+        // 2. 查询 kws_menu_rights,获取当前用户/角色有权限的 menuId
+        LambdaQueryWrapper<KwsMenuRights> rightsWrapper = Wrappers.lambdaQuery(KwsMenuRights.class)
+                .eq(KwsMenuRights::getDelFlag, Global.NO)
+                .select(KwsMenuRights::getMenuId);
+        if (CollectionUtils.isNotEmpty(pojo.getRoleIds())) {
+            rightsWrapper.in(KwsMenuRights::getRoleId, pojo.getRoleIds());
+        }
+        if (pojo.getEntId() != null) {
+            rightsWrapper.eq(KwsMenuRights::getEntId, pojo.getEntId());
+        }
+        List<KwsMenuRights> rightsRows = kwsMenuRightsMpMapper.selectList(rightsWrapper);
+        Set<Long> authorizedMenuIds = rightsRows.stream()
+                .map(KwsMenuRights::getMenuId)
+                .filter(Objects::nonNull)
+                .collect(Collectors.toSet());
+        if (authorizedMenuIds.isEmpty()) {
+            log.info("基于权限表补充按钮结束,kws_menu_rights 未查到授权菜单,entId={}, roleIds={}",
+                    pojo.getEntId(), pojo.getRoleIds());
+            return menuList;
+        }
+        log.debug("基于权限表补充按钮,授权菜单数={}", authorizedMenuIds.size());
+
+        // 3. 关联 kws_menu 查询有权限的按钮节点
+        LambdaQueryWrapper<KwsMenu> buttonWrapper = Wrappers.lambdaQuery(KwsMenu.class)
+                .eq(KwsMenu::getDelFlag, Global.NO)
+                .eq(KwsMenu::getType, MenuTypeEnum.BUTTON.getCode())
+                .eq(KwsMenu::getClientType, clientType)
+                .in(KwsMenu::getParentId, menuTypeIds)
+                .in(KwsMenu::getId, authorizedMenuIds)
+                .orderByAsc(KwsMenu::getSort);
+        appendUsingRolesFilter(buttonWrapper, pojo.getEntTypeList());
+
+        List<KwsMenu> buttons = kwsMenuMpMapper.selectList(buttonWrapper);
+        if (CollectionUtils.isEmpty(buttons)) {
+            log.info("基于权限表补充按钮结束,kws_menu 未匹配到按钮,clientType={}, entTypeList={}",
+                    clientType, pojo.getEntTypeList());
+            return menuList;
+        }
+        log.debug("基于权限表补充按钮,查询到按钮数={}", buttons.size());
+
+        // 4. 去重合并,避免与 findList 已返回的按钮重复
+        Set<Long> existingIds = menuList.stream().map(KwsMenuResVo::getId).collect(Collectors.toSet());
+        List<KwsMenuResVo> result = new ArrayList<>(menuList);
+        int addedCount = 0;
+        for (KwsMenu btn : buttons) {
+            if (!existingIds.contains(btn.getId())) {
+                KwsMenuResVo vo = new KwsMenuResVo();
+                BeanUtils.copyProperties(btn, vo);
+                result.add(vo);
+                addedCount++;
+            }
+        }
+        log.info("基于权限表补充按钮完成,新增按钮数={}, 合并后菜单总数={}", addedCount, result.size());
+        return result;
+    }
+
     /**
      * 补充按钮节点到菜单列表中
      * <p>