Commit 1ac68aca97df6718153c327a25f2bf0b04b3c464

Authored by puhui999
1 parent e4d3175f

CRM-回款计划:添加数据权限

yudao-module-crm/yudao-module-crm-api/src/main/java/cn/iocoder/yudao/module/crm/enums/common/CrmBizTypeEnum.java
... ... @@ -23,7 +23,8 @@ public enum CrmBizTypeEnum implements IntArrayValuable {
23 23 CRM_BUSINESS(4, "商机"),
24 24 CRM_CONTRACT(5, "合同"),
25 25 CRM_PRODUCT(6, "产品"),
26   - CRM_RECEIVABLE(7, "回款")
  26 + CRM_RECEIVABLE(7, "回款"),
  27 + CRM_RECEIVABLE_PLAN(8, "回款计划")
27 28 ;
28 29  
29 30 public static final int[] ARRAYS = Arrays.stream(values()).mapToInt(CrmBizTypeEnum::getType).toArray();
... ...
yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/controller/admin/receivable/CrmReceivablePlanController.java
... ... @@ -38,6 +38,7 @@ import java.util.Map;
38 38 import java.util.stream.Stream;
39 39  
40 40 import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;
  41 +import static cn.iocoder.yudao.framework.common.pojo.PageParam.PAGE_SIZE_NONE;
41 42 import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertListByFlatMap;
42 43 import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet;
43 44 import static cn.iocoder.yudao.framework.operatelog.core.enums.OperateTypeEnum.EXPORT;
... ... @@ -65,7 +66,7 @@ public class CrmReceivablePlanController {
65 66 @Operation(summary = "创建回款计划")
66 67 @PreAuthorize("@ss.hasPermission('crm:receivable-plan:create')")
67 68 public CommonResult<Long> createReceivablePlan(@Valid @RequestBody CrmReceivablePlanCreateReqVO createReqVO) {
68   - return success(receivablePlanService.createReceivablePlan(createReqVO));
  69 + return success(receivablePlanService.createReceivablePlan(createReqVO, getLoginUserId()));
69 70 }
70 71  
71 72 @PutMapping("/update")
... ... @@ -98,7 +99,7 @@ public class CrmReceivablePlanController {
98 99 @Operation(summary = "获得回款计划分页")
99 100 @PreAuthorize("@ss.hasPermission('crm:receivable-plan:query')")
100 101 public CommonResult<PageResult<CrmReceivablePlanRespVO>> getReceivablePlanPage(@Valid CrmReceivablePlanPageReqVO pageReqVO) {
101   - PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(pageReqVO);
  102 + PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(pageReqVO, getLoginUserId());
102 103 return success(convertDetailReceivablePlanPage(pageResult));
103 104 }
104 105  
... ... @@ -106,7 +107,7 @@ public class CrmReceivablePlanController {
106 107 @Operation(summary = "获得回款计划分页,基于指定客户")
107 108 public CommonResult<PageResult<CrmReceivablePlanRespVO>> getReceivablePlanPageByCustomer(@Valid CrmReceivablePlanPageReqVO pageReqVO) {
108 109 Assert.notNull(pageReqVO.getCustomerId(), "客户编号不能为空");
109   - PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPageByCustomer(pageReqVO);
  110 + PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPageByCustomerId(pageReqVO);
110 111 return success(convertDetailReceivablePlanPage(pageResult));
111 112 }
112 113  
... ... @@ -117,7 +118,8 @@ public class CrmReceivablePlanController {
117 118 @OperateLog(type = EXPORT)
118 119 public void exportReceivablePlanExcel(@Valid CrmReceivablePlanPageReqVO exportReqVO,
119 120 HttpServletResponse response) throws IOException {
120   - PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(exportReqVO);
  121 + exportReqVO.setPageSize(PAGE_SIZE_NONE);
  122 + PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(exportReqVO, getLoginUserId());
121 123 // 导出 Excel
122 124 ExcelUtils.write(response, "回款计划.xls", "数据", CrmReceivablePlanRespVO.class,
123 125 convertDetailReceivablePlanPage(pageResult).getList());
... ...
yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/dal/mysql/receivable/CrmReceivablePlanMapper.java
... ... @@ -3,10 +3,17 @@ package cn.iocoder.yudao.module.crm.dal.mysql.receivable;
3 3 import cn.iocoder.yudao.framework.common.pojo.PageResult;
4 4 import cn.iocoder.yudao.framework.mybatis.core.mapper.BaseMapperX;
5 5 import cn.iocoder.yudao.framework.mybatis.core.query.LambdaQueryWrapperX;
  6 +import cn.iocoder.yudao.framework.mybatis.core.query.MPJLambdaWrapperX;
6 7 import cn.iocoder.yudao.module.crm.controller.admin.receivable.vo.plan.CrmReceivablePlanPageReqVO;
7 8 import cn.iocoder.yudao.module.crm.dal.dataobject.receivable.CrmReceivablePlanDO;
  9 +import cn.iocoder.yudao.module.crm.enums.common.CrmBizTypeEnum;
  10 +import cn.iocoder.yudao.module.crm.util.CrmQueryWrapperUtils;
  11 +import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
8 12 import org.apache.ibatis.annotations.Mapper;
9 13  
  14 +import java.util.Collection;
  15 +import java.util.List;
  16 +
10 17 /**
11 18 * 回款计划 Mapper
12 19 *
... ... @@ -15,18 +22,37 @@ import org.apache.ibatis.annotations.Mapper;
15 22 @Mapper
16 23 public interface CrmReceivablePlanMapper extends BaseMapperX<CrmReceivablePlanDO> {
17 24  
18   - default PageResult<CrmReceivablePlanDO> selectPage(CrmReceivablePlanPageReqVO reqVO) {
19   - return selectPage(reqVO, new LambdaQueryWrapperX<CrmReceivablePlanDO>()
20   - .eqIfPresent(CrmReceivablePlanDO::getCustomerId, reqVO.getCustomerId())
21   - .eqIfPresent(CrmReceivablePlanDO::getContractId, reqVO.getContractId())
22   - .orderByDesc(CrmReceivablePlanDO::getId));
  25 + default int updateOwnerUserIdById(Long id, Long ownerUserId) {
  26 + return update(new LambdaUpdateWrapper<CrmReceivablePlanDO>()
  27 + .eq(CrmReceivablePlanDO::getId, id)
  28 + .set(CrmReceivablePlanDO::getOwnerUserId, ownerUserId));
23 29 }
24 30  
25   - default PageResult<CrmReceivablePlanDO> selectPageByCustomer(CrmReceivablePlanPageReqVO reqVO) {
  31 + default PageResult<CrmReceivablePlanDO> selectPageByCustomerId(CrmReceivablePlanPageReqVO reqVO) {
26 32 return selectPage(reqVO, new LambdaQueryWrapperX<CrmReceivablePlanDO>()
27 33 .eq(CrmReceivablePlanDO::getCustomerId, reqVO.getCustomerId()) // 必须传递
28 34 .eqIfPresent(CrmReceivablePlanDO::getContractId, reqVO.getContractId())
29 35 .orderByDesc(CrmReceivablePlanDO::getId));
30 36 }
31 37  
  38 + default PageResult<CrmReceivablePlanDO> selectPage(CrmReceivablePlanPageReqVO pageReqVO, Long userId) {
  39 + MPJLambdaWrapperX<CrmReceivablePlanDO> query = new MPJLambdaWrapperX<>();
  40 + // 拼接数据权限的查询条件
  41 + CrmQueryWrapperUtils.appendPermissionCondition(query, CrmBizTypeEnum.CRM_RECEIVABLE_PLAN.getType(), CrmReceivablePlanDO::getId,
  42 + userId, pageReqVO.getSceneType(), Boolean.FALSE);
  43 + // 拼接自身的查询条件
  44 + query.selectAll(CrmReceivablePlanDO.class)
  45 + .eqIfPresent(CrmReceivablePlanDO::getCustomerId, pageReqVO.getCustomerId())
  46 + .eqIfPresent(CrmReceivablePlanDO::getContractId, pageReqVO.getContractId())
  47 + .orderByDesc(CrmReceivablePlanDO::getId);
  48 + return selectJoinPage(pageReqVO, CrmReceivablePlanDO.class, query);
  49 + }
  50 +
  51 + default List<CrmReceivablePlanDO> selectBatchIds(Collection<Long> ids, Long userId) {
  52 + MPJLambdaWrapperX<CrmReceivablePlanDO> query = new MPJLambdaWrapperX<>();
  53 + // 拼接数据权限的查询条件
  54 + CrmQueryWrapperUtils.appendPermissionCondition(query, CrmBizTypeEnum.CRM_RECEIVABLE_PLAN.getType(), ids, userId);
  55 + return selectJoinList(CrmReceivablePlanDO.class, query);
  56 + }
  57 +
32 58 }
... ...
yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/permission/CrmPermissionServiceImpl.java
... ... @@ -138,6 +138,7 @@ public class CrmPermissionServiceImpl implements CrmPermissionService {
138 138 }
139 139  
140 140 @Override
  141 + @Transactional(rollbackFor = Exception.class)
141 142 public void deletePermission(Integer bizType, Long bizId) {
142 143 // 删除数据权限
143 144 int deletedCol = crmPermissionMapper.deletePermission(bizType, bizId);
... ...
yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/receivable/CrmReceivablePlanService.java
... ... @@ -6,8 +6,8 @@ import cn.iocoder.yudao.module.crm.controller.admin.receivable.vo.plan.CrmReceiv
6 6 import cn.iocoder.yudao.module.crm.controller.admin.receivable.vo.plan.CrmReceivablePlanUpdateReqVO;
7 7 import cn.iocoder.yudao.module.crm.dal.dataobject.customer.CrmCustomerDO;
8 8 import cn.iocoder.yudao.module.crm.dal.dataobject.receivable.CrmReceivablePlanDO;
9   -
10 9 import jakarta.validation.Valid;
  10 +
11 11 import java.util.Collection;
12 12 import java.util.List;
13 13  
... ... @@ -24,7 +24,7 @@ public interface CrmReceivablePlanService {
24 24 * @param createReqVO 创建信息
25 25 * @return 编号
26 26 */
27   - Long createReceivablePlan(@Valid CrmReceivablePlanCreateReqVO createReqVO);
  27 + Long createReceivablePlan(@Valid CrmReceivablePlanCreateReqVO createReqVO, Long userId);
28 28  
29 29 /**
30 30 * 更新回款计划
... ... @@ -62,9 +62,10 @@ public interface CrmReceivablePlanService {
62 62 * 数据权限:基于 {@link CrmReceivablePlanDO} 读取
63 63 *
64 64 * @param pageReqVO 分页查询
  65 + * @param userId 用户编号
65 66 * @return 回款计划分页
66 67 */
67   - PageResult<CrmReceivablePlanDO> getReceivablePlanPage(CrmReceivablePlanPageReqVO pageReqVO);
  68 + PageResult<CrmReceivablePlanDO> getReceivablePlanPage(CrmReceivablePlanPageReqVO pageReqVO, Long userId);
68 69  
69 70 /**
70 71 * 获得回款计划分页,基于指定客户
... ... @@ -74,6 +75,6 @@ public interface CrmReceivablePlanService {
74 75 * @param pageReqVO 分页查询
75 76 * @return 回款计划分页
76 77 */
77   - PageResult<CrmReceivablePlanDO> getReceivablePlanPageByCustomer(CrmReceivablePlanPageReqVO pageReqVO);
  78 + PageResult<CrmReceivablePlanDO> getReceivablePlanPageByCustomerId(CrmReceivablePlanPageReqVO pageReqVO);
78 79  
79 80 }
... ...
yudao-module-crm/yudao-module-crm-biz/src/main/java/cn/iocoder/yudao/module/crm/service/receivable/CrmReceivablePlanServiceImpl.java
... ... @@ -17,10 +17,12 @@ import cn.iocoder.yudao.module.crm.enums.permission.CrmPermissionLevelEnum;
17 17 import cn.iocoder.yudao.module.crm.framework.core.annotations.CrmPermission;
18 18 import cn.iocoder.yudao.module.crm.service.contract.CrmContractService;
19 19 import cn.iocoder.yudao.module.crm.service.customer.CrmCustomerService;
  20 +import cn.iocoder.yudao.module.crm.service.permission.CrmPermissionService;
  21 +import cn.iocoder.yudao.module.crm.service.permission.bo.CrmPermissionCreateReqBO;
  22 +import jakarta.annotation.Resource;
20 23 import org.springframework.stereotype.Service;
21 24 import org.springframework.validation.annotation.Validated;
22 25  
23   -import jakarta.annotation.Resource;
24 26 import java.util.Collection;
25 27 import java.util.List;
26 28  
... ... @@ -28,7 +30,7 @@ import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionU
28 30 import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.*;
29 31  
30 32 // TODO @liuhongfeng:参考 CrmReceivableServiceImpl 写的 todo 哈;
31   -// TODO @puhui999:数据权限
  33 +
32 34 /**
33 35 * 回款计划 Service 实现类
34 36 *
... ... @@ -45,9 +47,11 @@ public class CrmReceivablePlanServiceImpl implements CrmReceivablePlanService {
45 47 private CrmContractService contractService;
46 48 @Resource
47 49 private CrmCustomerService customerService;
  50 + @Resource
  51 + private CrmPermissionService crmPermissionService;
48 52  
49 53 @Override
50   - public Long createReceivablePlan(CrmReceivablePlanCreateReqVO createReqVO) {
  54 + public Long createReceivablePlan(CrmReceivablePlanCreateReqVO createReqVO, Long userId) {
51 55 // 插入
52 56 CrmReceivablePlanDO receivablePlan = CrmReceivablePlanConvert.INSTANCE.convert(createReqVO);
53 57 receivablePlan.setFinishStatus(false);
... ... @@ -55,29 +59,33 @@ public class CrmReceivablePlanServiceImpl implements CrmReceivablePlanService {
55 59 checkReceivablePlan(receivablePlan);
56 60  
57 61 receivablePlanMapper.insert(receivablePlan);
  62 + // 创建数据权限
  63 + crmPermissionService.createPermission(new CrmPermissionCreateReqBO().setBizType(CrmBizTypeEnum.CRM_RECEIVABLE_PLAN.getType())
  64 + .setBizId(receivablePlan.getId()).setUserId(userId).setLevel(CrmPermissionLevelEnum.OWNER.getLevel()));
58 65 // 返回
59 66 return receivablePlan.getId();
60 67 }
61 68  
62 69 private void checkReceivablePlan(CrmReceivablePlanDO receivablePlan) {
63 70  
64   - if(ObjectUtil.isNull(receivablePlan.getContractId())){
  71 + if (ObjectUtil.isNull(receivablePlan.getContractId())) {
65 72 throw exception(CONTRACT_NOT_EXISTS);
66 73 }
67 74  
68 75 CrmContractDO contract = contractService.getContract(receivablePlan.getContractId());
69   - if(ObjectUtil.isNull(contract)){
  76 + if (ObjectUtil.isNull(contract)) {
70 77 throw exception(CONTRACT_NOT_EXISTS);
71 78 }
72 79  
73 80 CrmCustomerDO customer = customerService.getCustomer(receivablePlan.getCustomerId());
74   - if(ObjectUtil.isNull(customer)){
  81 + if (ObjectUtil.isNull(customer)) {
75 82 throw exception(CUSTOMER_NOT_EXISTS);
76 83 }
77 84  
78 85 }
79 86  
80 87 @Override
  88 + @CrmPermission(bizType = CrmBizTypeEnum.CRM_RECEIVABLE_PLAN, bizId = "#updateReqVO.id", level = CrmPermissionLevelEnum.WRITE)
81 89 public void updateReceivablePlan(CrmReceivablePlanUpdateReqVO updateReqVO) {
82 90 // 校验存在
83 91 validateReceivablePlanExists(updateReqVO.getId());
... ... @@ -88,6 +96,7 @@ public class CrmReceivablePlanServiceImpl implements CrmReceivablePlanService {
88 96 }
89 97  
90 98 @Override
  99 + @CrmPermission(bizType = CrmBizTypeEnum.CRM_RECEIVABLE_PLAN, bizId = "#id", level = CrmPermissionLevelEnum.OWNER)
91 100 public void deleteReceivablePlan(Long id) {
92 101 // 校验存在
93 102 validateReceivablePlanExists(id);
... ... @@ -102,6 +111,7 @@ public class CrmReceivablePlanServiceImpl implements CrmReceivablePlanService {
102 111 }
103 112  
104 113 @Override
  114 + @CrmPermission(bizType = CrmBizTypeEnum.CRM_RECEIVABLE_PLAN, bizId = "#id", level = CrmPermissionLevelEnum.READ)
105 115 public CrmReceivablePlanDO getReceivablePlan(Long id) {
106 116 return receivablePlanMapper.selectById(id);
107 117 }
... ... @@ -115,14 +125,14 @@ public class CrmReceivablePlanServiceImpl implements CrmReceivablePlanService {
115 125 }
116 126  
117 127 @Override
118   - public PageResult<CrmReceivablePlanDO> getReceivablePlanPage(CrmReceivablePlanPageReqVO pageReqVO) {
119   - return receivablePlanMapper.selectPage(pageReqVO);
  128 + public PageResult<CrmReceivablePlanDO> getReceivablePlanPage(CrmReceivablePlanPageReqVO pageReqVO, Long userId) {
  129 + return receivablePlanMapper.selectPage(pageReqVO, userId);
120 130 }
121 131  
122 132 @Override
123 133 @CrmPermission(bizType = CrmBizTypeEnum.CRM_CUSTOMER, bizId = "#pageReqVO.customerId", level = CrmPermissionLevelEnum.READ)
124   - public PageResult<CrmReceivablePlanDO> getReceivablePlanPageByCustomer(CrmReceivablePlanPageReqVO pageReqVO) {
125   - return receivablePlanMapper.selectPageByCustomer(pageReqVO);
  134 + public PageResult<CrmReceivablePlanDO> getReceivablePlanPageByCustomerId(CrmReceivablePlanPageReqVO pageReqVO) {
  135 + return receivablePlanMapper.selectPageByCustomerId(pageReqVO);
126 136 }
127 137  
128 138 }
... ...
yudao-module-crm/yudao-module-crm-biz/src/test/java/cn/iocoder/yudao/module/crm/service/receivable/CrmCrmReceivablePlanServiceImplTest.java
... ... @@ -7,12 +7,12 @@ import cn.iocoder.yudao.module.crm.controller.admin.receivable.vo.plan.CrmReceiv
7 7 import cn.iocoder.yudao.module.crm.controller.admin.receivable.vo.plan.CrmReceivablePlanUpdateReqVO;
8 8 import cn.iocoder.yudao.module.crm.dal.dataobject.receivable.CrmReceivablePlanDO;
9 9 import cn.iocoder.yudao.module.crm.dal.mysql.receivable.CrmReceivablePlanMapper;
  10 +import jakarta.annotation.Resource;
10 11 import org.junit.jupiter.api.Disabled;
11 12 import org.junit.jupiter.api.Test;
12 13 import org.springframework.context.annotation.Import;
13 14  
14   -import jakarta.annotation.Resource;
15   -
  15 +import static cn.iocoder.yudao.framework.common.pojo.PageParam.PAGE_SIZE_NONE;
16 16 import static cn.iocoder.yudao.framework.common.util.object.ObjectUtils.cloneIgnoreId;
17 17 import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertPojoEquals;
18 18 import static cn.iocoder.yudao.framework.test.core.util.AssertUtils.assertServiceException;
... ... @@ -22,6 +22,7 @@ import static cn.iocoder.yudao.module.crm.enums.ErrorCodeConstants.RECEIVABLE_PL
22 22 import static org.junit.jupiter.api.Assertions.*;
23 23  
24 24 // TODO 芋艿:后续,需要补充测试用例
  25 +
25 26 /**
26 27 * {@link CrmReceivablePlanServiceImpl} 的单元测试类
27 28 *
... ... @@ -43,7 +44,7 @@ public class CrmCrmReceivablePlanServiceImplTest extends BaseDbUnitTest {
43 44 CrmReceivablePlanCreateReqVO reqVO = randomPojo(CrmReceivablePlanCreateReqVO.class);
44 45  
45 46 // 调用
46   - Long receivablePlanId = receivablePlanService.createReceivablePlan(reqVO);
  47 + Long receivablePlanId = receivablePlanService.createReceivablePlan(reqVO, 1L);
47 48 // 断言
48 49 assertNotNull(receivablePlanId);
49 50 // 校验记录的属性是否正确
... ... @@ -87,8 +88,8 @@ public class CrmCrmReceivablePlanServiceImplTest extends BaseDbUnitTest {
87 88  
88 89 // 调用
89 90 receivablePlanService.deleteReceivablePlan(id);
90   - // 校验数据不存在了
91   - assertNull(crmReceivablePlanMapper.selectById(id));
  91 + // 校验数据不存在了
  92 + assertNull(crmReceivablePlanMapper.selectById(id));
92 93 }
93 94  
94 95 @Test
... ... @@ -103,34 +104,34 @@ public class CrmCrmReceivablePlanServiceImplTest extends BaseDbUnitTest {
103 104 @Test
104 105 @Disabled // TODO 请修改 null 为需要的值,然后删除 @Disabled 注解
105 106 public void testGetReceivablePlanPage() {
106   - // mock 数据
107   - CrmReceivablePlanDO dbReceivablePlan = randomPojo(CrmReceivablePlanDO.class, o -> { // 等会查询到
108   - o.setPeriod(null);
109   - o.setReturnTime(null);
110   - o.setRemindDays(null);
111   - o.setRemindTime(null);
112   - o.setCustomerId(null);
113   - o.setContractId(null);
114   - o.setOwnerUserId(null);
115   - o.setRemark(null);
116   - o.setCreateTime(null);
117   - });
118   - crmReceivablePlanMapper.insert(dbReceivablePlan);
119   - // 测试 customerId 不匹配
120   - crmReceivablePlanMapper.insert(cloneIgnoreId(dbReceivablePlan, o -> o.setCustomerId(null)));
121   - // 测试 contractId 不匹配
122   - crmReceivablePlanMapper.insert(cloneIgnoreId(dbReceivablePlan, o -> o.setContractId(null)));
123   - // 准备参数
124   - CrmReceivablePlanPageReqVO reqVO = new CrmReceivablePlanPageReqVO();
125   - reqVO.setCustomerId(null);
126   - reqVO.setContractId(null);
127   -
128   - // 调用
129   - PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(reqVO);
130   - // 断言
131   - assertEquals(1, pageResult.getTotal());
132   - assertEquals(1, pageResult.getList().size());
133   - assertPojoEquals(dbReceivablePlan, pageResult.getList().get(0));
  107 + // mock 数据
  108 + CrmReceivablePlanDO dbReceivablePlan = randomPojo(CrmReceivablePlanDO.class, o -> { // 等会查询到
  109 + o.setPeriod(null);
  110 + o.setReturnTime(null);
  111 + o.setRemindDays(null);
  112 + o.setRemindTime(null);
  113 + o.setCustomerId(null);
  114 + o.setContractId(null);
  115 + o.setOwnerUserId(null);
  116 + o.setRemark(null);
  117 + o.setCreateTime(null);
  118 + });
  119 + crmReceivablePlanMapper.insert(dbReceivablePlan);
  120 + // 测试 customerId 不匹配
  121 + crmReceivablePlanMapper.insert(cloneIgnoreId(dbReceivablePlan, o -> o.setCustomerId(null)));
  122 + // 测试 contractId 不匹配
  123 + crmReceivablePlanMapper.insert(cloneIgnoreId(dbReceivablePlan, o -> o.setContractId(null)));
  124 + // 准备参数
  125 + CrmReceivablePlanPageReqVO reqVO = new CrmReceivablePlanPageReqVO();
  126 + reqVO.setCustomerId(null);
  127 + reqVO.setContractId(null);
  128 + reqVO.setPageSize(PAGE_SIZE_NONE);
  129 + // 调用
  130 + PageResult<CrmReceivablePlanDO> pageResult = receivablePlanService.getReceivablePlanPage(reqVO, 1L);
  131 + // 断言
  132 + assertEquals(1, pageResult.getTotal());
  133 + assertEquals(1, pageResult.getList().size());
  134 + assertPojoEquals(dbReceivablePlan, pageResult.getList().get(0));
134 135 }
135 136  
136 137 }
... ...
yudao-module-infra/yudao-module-infra-biz/src/main/resources/codegen/vue/api/api.js.vm
... ... @@ -63,7 +63,7 @@ export function export${simpleClassName}Excel(params) {
63 63 responseType: 'blob'
64 64 })
65 65 }
66   -## 特殊:主子表专属逻辑 TODO @puhui999:下面方法的【空格】不太对
  66 +## 特殊:主子表专属逻辑
67 67 #foreach ($subTable in $subTables)
68 68 #set ($index = $foreach.count - 1)
69 69 #set ($subSimpleClassName = $subSimpleClassNames.get($index))
... ... @@ -76,7 +76,7 @@ export function export${simpleClassName}Excel(params) {
76 76  
77 77 // ==================== 子表($subTable.classComment) ====================
78 78 ## 情况一:MASTER_ERP 时,需要分查询页子表
79   - #if ( $table.templateType == 11 )
  79 + #if ($table.templateType == 11)
80 80 // 获得${subTable.classComment}分页
81 81 export function get${subSimpleClassName}Page(params) {
82 82 return request({
... ... @@ -87,7 +87,7 @@ export function export${simpleClassName}Excel(params) {
87 87 }
88 88 ## 情况二:非 MASTER_ERP 时,需要列表查询子表
89 89 #else
90   - #if ( $subTable.subJoinMany )
  90 + #if ($subTable.subJoinMany)
91 91 // 获得${subTable.classComment}列表
92 92 export function get${subSimpleClassName}ListBy${SubJoinColumnName}(${subJoinColumn.javaField}) {
93 93 return request({
... ... @@ -106,7 +106,7 @@ export function export${simpleClassName}Excel(params) {
106 106 #end
107 107 #end
108 108 ## 特殊:MASTER_ERP 时,支持单个的新增、修改、删除操作
109   - #if ( $table.templateType == 11 )
  109 + #if ($table.templateType == 11)
110 110 // 新增${subTable.classComment}
111 111 export function create${subSimpleClassName}(data) {
112 112 return request({
... ... @@ -115,7 +115,6 @@ export function export${simpleClassName}Excel(params) {
115 115 data
116 116 })
117 117 }
118   -
119 118 // 修改${subTable.classComment}
120 119 export function update${subSimpleClassName}(data) {
121 120 return request({
... ... @@ -124,7 +123,6 @@ export function export${simpleClassName}Excel(params) {
124 123 data
125 124 })
126 125 }
127   -
128 126 // 删除${subTable.classComment}
129 127 export function delete${subSimpleClassName}(id) {
130 128 return request({
... ... @@ -132,7 +130,6 @@ export function export${simpleClassName}Excel(params) {
132 130 method: 'delete'
133 131 })
134 132 }
135   -
136 133 // 获得${subTable.classComment}
137 134 export function get${subSimpleClassName}(id) {
138 135 return request({
... ...