From f5ea270be3a0580b53f10affeaa8dc066349cc6a Mon Sep 17 00:00:00 2001 From: YunaiV Date: Thu, 16 Nov 2023 12:55:43 +0800 Subject: [PATCH] =?UTF-8?q?=E9=83=A8=E9=97=A8=EF=BC=9A=E4=BC=98=E5=8C=96?= =?UTF-8?q?=E7=88=B6=E9=83=A8=E9=97=A8=E7=9A=84=E6=A0=A1=E9=AA=8C=E9=80=BB?= =?UTF-8?q?=E8=BE=91=EF=BC=8C=E4=B8=BA=E4=BB=A3=E7=A0=81=E7=94=9F=E6=88=90?= =?UTF-8?q?=E5=81=9A=E4=B8=AA=E9=93=BA=E5=9E=AB=EF=BC=9F=EF=BC=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../module/system/enums/dept/DeptIdEnum.java | 20 ----- .../system/dal/dataobject/dept/DeptDO.java | 2 + .../system/service/dept/DeptServiceImpl.java | 76 +++++++++++-------- .../service/dept/DeptServiceImplTest.java | 5 +- 4 files changed, 48 insertions(+), 55 deletions(-) delete mode 100644 yudao-module-system/yudao-module-system-api/src/main/java/cn/iocoder/yudao/module/system/enums/dept/DeptIdEnum.java diff --git a/yudao-module-system/yudao-module-system-api/src/main/java/cn/iocoder/yudao/module/system/enums/dept/DeptIdEnum.java b/yudao-module-system/yudao-module-system-api/src/main/java/cn/iocoder/yudao/module/system/enums/dept/DeptIdEnum.java deleted file mode 100644 index 2a7effec2..000000000 --- a/yudao-module-system/yudao-module-system-api/src/main/java/cn/iocoder/yudao/module/system/enums/dept/DeptIdEnum.java +++ /dev/null @@ -1,20 +0,0 @@ -package cn.iocoder.yudao.module.system.enums.dept; - -import lombok.AllArgsConstructor; -import lombok.Getter; - -/** - * 部门编号枚举 - */ -@Getter -@AllArgsConstructor -public enum DeptIdEnum { - - /** - * 根节点 - */ - ROOT(0L); - - private final Long id; - -} diff --git a/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java b/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java index 31f90cfc4..a59fa8b6e 100644 --- a/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java +++ b/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/dal/dataobject/dept/DeptDO.java @@ -21,6 +21,8 @@ import lombok.EqualsAndHashCode; @EqualsAndHashCode(callSuper = true) public class DeptDO extends TenantBaseDO { + public static final Long PARENT_ID_ROOT = 0L; + /** * 部门ID */ diff --git a/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImpl.java b/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImpl.java index cde5a0021..2253daee7 100644 --- a/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImpl.java +++ b/yudao-module-system/yudao-module-system-biz/src/main/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImpl.java @@ -11,7 +11,6 @@ import cn.iocoder.yudao.module.system.convert.dept.DeptConvert; import cn.iocoder.yudao.module.system.dal.dataobject.dept.DeptDO; import cn.iocoder.yudao.module.system.dal.mysql.dept.DeptMapper; import cn.iocoder.yudao.module.system.dal.redis.RedisKeyConstants; -import cn.iocoder.yudao.module.system.enums.dept.DeptIdEnum; import com.google.common.annotations.VisibleForTesting; import lombok.extern.slf4j.Slf4j; import org.springframework.cache.annotation.CacheEvict; @@ -42,14 +41,17 @@ public class DeptServiceImpl implements DeptService { @Override @CacheEvict(cacheNames = RedisKeyConstants.DEPT_CHILDREN_ID_LIST, allEntries = true) // allEntries 清空所有缓存,因为操作一个部门,涉及到多个缓存 - public Long createDept(DeptCreateReqVO reqVO) { - // 校验正确性 - if (reqVO.getParentId() == null) { - reqVO.setParentId(DeptIdEnum.ROOT.getId()); + public Long createDept(DeptCreateReqVO createReqVO) { + if (createReqVO.getParentId() == null) { + createReqVO.setParentId(DeptDO.PARENT_ID_ROOT); } - validateForCreateOrUpdate(null, reqVO.getParentId(), reqVO.getName()); + // 校验父部门的有效性 + validateParentDept(null, createReqVO.getParentId()); + // 校验部门名的唯一性 + validateDeptNameUnique(null, createReqVO.getParentId(), createReqVO.getName()); + // 插入部门 - DeptDO dept = DeptConvert.INSTANCE.convert(reqVO); + DeptDO dept = DeptConvert.INSTANCE.convert(createReqVO); deptMapper.insert(dept); return dept.getId(); } @@ -57,14 +59,19 @@ public class DeptServiceImpl implements DeptService { @Override @CacheEvict(cacheNames = RedisKeyConstants.DEPT_CHILDREN_ID_LIST, allEntries = true) // allEntries 清空所有缓存,因为操作一个部门,涉及到多个缓存 - public void updateDept(DeptUpdateReqVO reqVO) { - // 校验正确性 - if (reqVO.getParentId() == null) { - reqVO.setParentId(DeptIdEnum.ROOT.getId()); + public void updateDept(DeptUpdateReqVO updateReqVO) { + if (updateReqVO.getParentId() == null) { + updateReqVO.setParentId(DeptDO.PARENT_ID_ROOT); } - validateForCreateOrUpdate(reqVO.getId(), reqVO.getParentId(), reqVO.getName()); + // 校验自己存在 + validateDeptExists(updateReqVO.getId()); + // 校验父部门的有效性 + validateParentDept(updateReqVO.getId(), updateReqVO.getParentId()); + // 校验部门名的唯一性 + validateDeptNameUnique(updateReqVO.getId(), updateReqVO.getParentId(), updateReqVO.getName()); + // 更新部门 - DeptDO updateObj = DeptConvert.INSTANCE.convert(reqVO); + DeptDO updateObj = DeptConvert.INSTANCE.convert(updateReqVO); deptMapper.updateById(updateObj); } @@ -82,15 +89,6 @@ public class DeptServiceImpl implements DeptService { deptMapper.deleteById(id); } - private void validateForCreateOrUpdate(Long id, Long parentId, String name) { - // 校验自己存在 - validateDeptExists(id); - // 校验父部门的有效性 - validateParentDept(id, parentId); - // 校验部门名的唯一性 - validateDeptNameUnique(id, parentId, name); - } - @VisibleForTesting void validateDeptExists(Long id) { if (id == null) { @@ -104,22 +102,36 @@ public class DeptServiceImpl implements DeptService { @VisibleForTesting void validateParentDept(Long id, Long parentId) { - if (parentId == null || DeptIdEnum.ROOT.getId().equals(parentId)) { + if (parentId == null || DeptDO.PARENT_ID_ROOT.equals(parentId)) { return; } - // 不能设置自己为父部门 - if (parentId.equals(id)) { + // 1. 不能设置自己为父部门 + if (Objects.equals(id, parentId)) { throw exception(DEPT_PARENT_ERROR); } - // 父岗位不存在 - DeptDO dept = deptMapper.selectById(parentId); - if (dept == null) { + // 2. 父部门不存在 + DeptDO parentDept = deptMapper.selectById(parentId); + if (parentDept == null) { throw exception(DEPT_PARENT_NOT_EXITS); } - // 父部门不能是原来的子部门 - List children = getChildDeptList(id); - if (children.stream().anyMatch(dept1 -> dept1.getId().equals(parentId))) { - throw exception(DEPT_PARENT_IS_CHILD); + // 3. 递归校验父部门,如果父部门是自己的子部门,则报错,避免形成环路 + if (id == null) { // id 为空,说明新增,不需要考虑环路 + return; + } + for (int i = 0; i < Short.MAX_VALUE; i++) { + // 3.1 校验环路 + parentId = parentDept.getParentId(); + if (Objects.equals(id, parentId)) { + throw exception(DEPT_PARENT_IS_CHILD); + } + // 3.2 继续递归下一级父部门 + if (parentId == null || DeptDO.PARENT_ID_ROOT.equals(parentId)) { + break; + } + parentDept = deptMapper.selectById(parentId); + if (parentDept == null) { + break; + } } } diff --git a/yudao-module-system/yudao-module-system-biz/src/test/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImplTest.java b/yudao-module-system/yudao-module-system-biz/src/test/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImplTest.java index cf9dc5a35..99c44f777 100644 --- a/yudao-module-system/yudao-module-system-biz/src/test/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImplTest.java +++ b/yudao-module-system/yudao-module-system-biz/src/test/java/cn/iocoder/yudao/module/system/service/dept/DeptServiceImplTest.java @@ -8,7 +8,6 @@ import cn.iocoder.yudao.module.system.controller.admin.dept.vo.dept.DeptListReqV import cn.iocoder.yudao.module.system.controller.admin.dept.vo.dept.DeptUpdateReqVO; import cn.iocoder.yudao.module.system.dal.dataobject.dept.DeptDO; import cn.iocoder.yudao.module.system.dal.mysql.dept.DeptMapper; -import cn.iocoder.yudao.module.system.enums.dept.DeptIdEnum; import org.junit.jupiter.api.Test; import org.springframework.context.annotation.Import; @@ -41,7 +40,7 @@ public class DeptServiceImplTest extends BaseDbUnitTest { public void testCreateDept() { // 准备参数 DeptCreateReqVO reqVO = randomPojo(DeptCreateReqVO.class, o -> { - o.setParentId(DeptIdEnum.ROOT.getId()); + o.setParentId(DeptDO.PARENT_ID_ROOT); o.setStatus(randomCommonStatus()); }); @@ -62,7 +61,7 @@ public class DeptServiceImplTest extends BaseDbUnitTest { // 准备参数 DeptUpdateReqVO reqVO = randomPojo(DeptUpdateReqVO.class, o -> { // 设置更新的 ID - o.setParentId(DeptIdEnum.ROOT.getId()); + o.setParentId(DeptDO.PARENT_ID_ROOT); o.setId(dbDeptDO.getId()); o.setStatus(randomCommonStatus()); });