diff --git a/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/enums/ErrorCodeConstants.java b/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/enums/ErrorCodeConstants.java
index 9cb9ac62f..149025974 100644
--- a/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/enums/ErrorCodeConstants.java
+++ b/cf-module-system/cf-module-system-api/src/main/java/com/cf/imes/module/system/enums/ErrorCodeConstants.java
@@ -71,6 +71,7 @@ public class ErrorCodeConstants {
public static final ErrorCode DEPT_NOT_ENABLE = new ErrorCode(1_002_004_006, "部门({})不处于开启状态,不允许选择");
public static final ErrorCode DEPT_PARENT_IS_CHILD = new ErrorCode(1_002_004_007, "不能设置自己的子部门为父部门");
public static final ErrorCode DEPT_USER_OPER_NOT_ALLOW = new ErrorCode(1_002_015_008, "不允许操作用户自身部门");
+ public static final ErrorCode PARENT_DEPT_USER_OPER_NOT_ALLOW = new ErrorCode(1_002_015_008, "不允许操作用户自身部门及其上级部门");
public static final ErrorCode DEPT_DISABLE = new ErrorCode(1_002_004_006, "部门({})已被禁用");
// ========== 岗位模块 1-002-005-000 ==========
@@ -94,6 +95,7 @@ public class ErrorCodeConstants {
// ========== 通知公告 1-002-008-000 ==========
public static final ErrorCode NOTICE_NOT_FOUND = new ErrorCode(1_002_008_001, "当前通知公告不存在");
public static final ErrorCode NOTICE_NAME_UNIQE_ERROR = new ErrorCode(1_002_008_002, "公告标题已存在,请编辑后重试");
+ public static final ErrorCode NOTICE_BUILDIN_MODIFY_PERMISSION_ERROR = new ErrorCode(1_002_008_003, "内置通知公告编辑权限不足");
// ========== 短信渠道 1-002-011-000 ==========
public static final ErrorCode SMS_CHANNEL_NOT_EXISTS = new ErrorCode(1_002_011_000, "短信渠道不存在");
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticePageReqVO.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticePageReqVO.java
index 1de067edc..8fedeaf26 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticePageReqVO.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticePageReqVO.java
@@ -21,4 +21,9 @@ public class NoticePageReqVO extends PageParam {
@CommonStatus
private Integer status;
+ @Schema(description = "组织id")
+ private Long organId;
+
+ @Schema(description = "通知公告来源")
+ private Integer source;
}
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticeSaveReqVO.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticeSaveReqVO.java
index 47cc6c34a..5dc9113b6 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticeSaveReqVO.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/controller/admin/notice/vo/NoticeSaveReqVO.java
@@ -25,6 +25,7 @@ public class NoticeSaveReqVO {
private Integer type;
@Schema(description = "公告内容", requiredMode = Schema.RequiredMode.REQUIRED, example = "半生编码")
+ @NotBlank(message = "公告内容不能为空")
private String content;
@Schema(description = "状态,参见 CommonStatusEnum 枚举类", requiredMode = Schema.RequiredMode.REQUIRED, example = "1")
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/dataobject/notice/NoticeDO.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/dataobject/notice/NoticeDO.java
index 02ffc404b..380ad33a7 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/dataobject/notice/NoticeDO.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/dataobject/notice/NoticeDO.java
@@ -1,7 +1,10 @@
package com.cf.imes.module.system.dal.dataobject.notice;
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
import com.cf.imes.framework.common.enums.CommonStatusEnum;
import com.cf.imes.framework.mybatis.core.dataobject.BaseDO;
+import com.cf.imes.module.system.enums.notice.NoticeSourceEnum;
import com.cf.imes.module.system.enums.notice.NoticeTypeEnum;
import com.baomidou.mybatisplus.annotation.KeySequence;
import com.baomidou.mybatisplus.annotation.TableName;
@@ -33,6 +36,14 @@ public class NoticeDO extends BaseDO {
* 枚举 {@link NoticeTypeEnum}
*/
private Integer type;
+
+ /**
+ * 公告来源
+ *
+ * 枚举 {@link NoticeSourceEnum}
+ */
+ private NoticeSourceEnum source;
+
/**
* 公告内容
*/
@@ -44,4 +55,9 @@ public class NoticeDO extends BaseDO {
*/
private Integer status;
+ /**
+ * 组织ID
+ */
+ @TableField(fill = FieldFill.INSERT_UPDATE)
+ private Long organId;
}
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/mysql/notice/NoticeMapper.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/mysql/notice/NoticeMapper.java
index 8b36d8ca3..7a7af7993 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/mysql/notice/NoticeMapper.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/dal/mysql/notice/NoticeMapper.java
@@ -3,18 +3,33 @@ package com.cf.imes.module.system.dal.mysql.notice;
import com.cf.imes.framework.common.pojo.PageResult;
import com.cf.imes.framework.mybatis.core.mapper.BaseMapperX;
import com.cf.imes.framework.mybatis.core.query.LambdaQueryWrapperX;
+import com.cf.imes.framework.organ.core.context.OrganContextHolder;
import com.cf.imes.module.system.controller.admin.notice.vo.NoticePageReqVO;
import com.cf.imes.module.system.dal.dataobject.notice.NoticeDO;
+import com.cf.imes.module.system.enums.notice.NoticeSourceEnum;
import org.apache.ibatis.annotations.Mapper;
@Mapper
public interface NoticeMapper extends BaseMapperX {
default PageResult selectPage(NoticePageReqVO reqVO) {
+ if (NoticeSourceEnum.SYSTEM.getSource().equals(reqVO.getSource())) {
+ // 超管只看内置的
+ return selectPage(reqVO, new LambdaQueryWrapperX()
+ .likeIfPresent(NoticeDO::getTitle, reqVO.getTitle())
+ .eqIfPresent(NoticeDO::getStatus, reqVO.getStatus())
+ .eqIfPresent(NoticeDO::getSource, NoticeSourceEnum.SYSTEM)
+ .orderByDesc(NoticeDO::getId));
+ }
+ // 普通用户查机构下的和内置的
return selectPage(reqVO, new LambdaQueryWrapperX()
.likeIfPresent(NoticeDO::getTitle, reqVO.getTitle())
.eqIfPresent(NoticeDO::getStatus, reqVO.getStatus())
- .orderByDesc(NoticeDO::getId));
+ .and(wr -> wr.or(wrapper -> wrapper
+ .eq(NoticeDO::getOrganId, OrganContextHolder.getOrganId())
+ .eq(NoticeDO::getSource, NoticeSourceEnum.CUSTOM))
+ .or(wrapper -> wrapper.eq(NoticeDO::getSource, NoticeSourceEnum.SYSTEM)))
+ .orderByDesc(NoticeDO::getId));
}
}
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/enums/notice/NoticeSourceEnum.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/enums/notice/NoticeSourceEnum.java
new file mode 100644
index 000000000..d2de57e1e
--- /dev/null
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/enums/notice/NoticeSourceEnum.java
@@ -0,0 +1,38 @@
+package com.cf.imes.module.system.enums.notice;
+
+import com.baomidou.mybatisplus.annotation.EnumValue;
+import com.fasterxml.jackson.annotation.JsonCreator;
+import lombok.AllArgsConstructor;
+import lombok.Getter;
+
+/**
+ * 通知公告来源
+ *
+ * @author Gqr
+ * @since 2024/7/5 9:25
+ */
+@Getter
+@AllArgsConstructor
+public enum NoticeSourceEnum {
+ /**
+ * 内置
+ */
+ SYSTEM(0),
+ /**
+ * 自定义
+ */
+ CUSTOM(1);
+
+ @EnumValue
+ private final Integer source;
+
+ @JsonCreator
+ public static NoticeSourceEnum fromSource(Integer source) {
+ for (NoticeSourceEnum value : values()) {
+ if (value.getSource().equals(source)) {
+ return value;
+ }
+ }
+ return null;
+ }
+}
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/dept/DeptServiceImpl.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/dept/DeptServiceImpl.java
index 88ba11fd9..f391c6fef 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/dept/DeptServiceImpl.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/dept/DeptServiceImpl.java
@@ -36,6 +36,7 @@ import static com.cf.imes.framework.common.exception.util.ServiceExceptionUtil.e
import static com.cf.imes.framework.common.util.collection.CollectionUtils.convertSet;
import static com.cf.imes.module.system.dal.redis.RedisKeyConstants.OAUTH2_ACCESS_TOKEN;
import static com.cf.imes.module.system.enums.ErrorCodeConstants.DEPT_USER_OPER_NOT_ALLOW;
+import static com.cf.imes.module.system.enums.ErrorCodeConstants.PARENT_DEPT_USER_OPER_NOT_ALLOW;
/**
* 部门 Service 实现类
@@ -105,14 +106,14 @@ public class DeptServiceImpl implements DeptService {
@CacheEvict(cacheNames = RedisKeyConstants.DEPT_CHILDREN_ID_LIST,
allEntries = true) // allEntries 清空所有缓存,因为操作一个部门,涉及到多个缓存
public void deleteDept(Long id) {
- // 校验部门内用户操作
- checkCurrentWhenOperate(id);
// 校验是否存在
validateDeptExists(id);
// 校验是否有子部门
if (deptMapper.selectCountByParentId(id) > 0) {
throw ServiceExceptionUtil.exception(ErrorCodeConstants.DEPT_EXITS_CHILDREN);
}
+ // 校验部门内用户操作
+ checkCurrentWhenOperate(id);
// 删除部门
deptMapper.deleteById(id);
// 删除关联的用户
@@ -153,9 +154,15 @@ public class DeptServiceImpl implements DeptService {
*/
private void checkCurrentWhenOperate(Long deptId) {
LoginUser loginUser = SecurityFrameworkUtils.getLoginUser();
- if (ObjectUtil.isNotNull(loginUser) && ObjectUtil.equal(deptId, loginUser.getDeptId())) {
+ Long currentDeptId = loginUser.getDeptId();
+ if (ObjectUtil.isNotNull(loginUser) && ObjectUtil.equal(deptId, currentDeptId)) {
throw exception(DEPT_USER_OPER_NOT_ALLOW);
}
+ // 递归查询所有下级,如果当前用户在范围内不允许操作
+ List childDeptList = getChildDeptList(deptId);
+ childDeptList.stream().filter(d -> d.getId().equals(currentDeptId)).findAny().ifPresent(deptDO -> {
+ throw exception(PARENT_DEPT_USER_OPER_NOT_ALLOW);
+ });
}
@VisibleForTesting
diff --git a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/notice/NoticeServiceImpl.java b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/notice/NoticeServiceImpl.java
index 2e7accf72..b852545c6 100644
--- a/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/notice/NoticeServiceImpl.java
+++ b/cf-module-system/cf-module-system-biz/src/main/java/com/cf/imes/module/system/service/notice/NoticeServiceImpl.java
@@ -1,17 +1,21 @@
package com.cf.imes.module.system.service.notice;
import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.extra.spring.SpringUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.cf.imes.framework.common.exception.util.ServiceExceptionUtil;
import com.cf.imes.framework.common.pojo.PageResult;
import com.cf.imes.framework.common.util.object.BeanUtils;
import com.cf.imes.framework.mybatis.core.query.LambdaQueryWrapperX;
+import com.cf.imes.framework.organ.core.aop.OrganIgnore;
+import com.cf.imes.framework.organ.core.context.OrganContextHolder;
+import com.cf.imes.framework.security.core.util.SecurityFrameworkUtils;
import com.cf.imes.module.system.controller.admin.notice.vo.NoticePageReqVO;
import com.cf.imes.module.system.controller.admin.notice.vo.NoticeSaveReqVO;
import com.cf.imes.module.system.dal.dataobject.notice.NoticeDO;
import com.cf.imes.module.system.dal.mysql.notice.NoticeMapper;
import com.cf.imes.module.system.enums.ErrorCodeConstants;
-import com.google.common.annotations.VisibleForTesting;
+import com.cf.imes.module.system.enums.notice.NoticeSourceEnum;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
@@ -30,11 +34,19 @@ public class NoticeServiceImpl implements NoticeService {
@Resource
private NoticeMapper noticeMapper;
+
+ private NoticeServiceImpl getSelf() {
+ return SpringUtil.getBean(getClass());
+ }
+
@Override
public Long createNotice(NoticeSaveReqVO createReqVO) {
// 标题唯一性校验
validateNameExists(createReqVO);
NoticeDO notice = BeanUtils.toBean(createReqVO, NoticeDO.class);
+
+ // 超管创建的都是内置公告
+ modifySource(notice);
noticeMapper.insert(notice);
return notice.getId();
}
@@ -42,24 +54,32 @@ public class NoticeServiceImpl implements NoticeService {
@Override
public void updateNotice(NoticeSaveReqVO updateReqVO) {
// 校验是否存在
- validateNoticeExists(updateReqVO.getId());
+ getSelf().validateNoticeExists(updateReqVO.getId());
// 标题唯一性校验
- validateNameExists(updateReqVO);
+ getSelf().validateNameExists(updateReqVO);
// 更新通知公告
NoticeDO updateObj = BeanUtils.toBean(updateReqVO, NoticeDO.class);
+ // 超管创建的都是内置公告
+ modifySource(updateObj);
noticeMapper.updateById(updateObj);
}
@Override
public void deleteNotice(Long id) {
// 校验是否存在
- validateNoticeExists(id);
+ getSelf().validateNoticeExists(id);
// 删除通知公告
noticeMapper.deleteById(id);
}
@Override
+ @OrganIgnore
public PageResult getNoticePage(NoticePageReqVO reqVO) {
+ boolean isSuperAdmin = SecurityFrameworkUtils.isSuperAdmin();
+ // 超管查看内置公告
+ if (isSuperAdmin) {
+ reqVO.setSource(NoticeSourceEnum.SYSTEM.getSource());
+ }
return noticeMapper.selectPage(reqVO);
}
@@ -68,7 +88,7 @@ public class NoticeServiceImpl implements NoticeService {
return noticeMapper.selectById(id);
}
- @VisibleForTesting
+ @OrganIgnore
public void validateNoticeExists(Long id) {
if (id == null) {
return;
@@ -77,6 +97,13 @@ public class NoticeServiceImpl implements NoticeService {
if (notice == null) {
throw ServiceExceptionUtil.exception(ErrorCodeConstants.NOTICE_NOT_FOUND);
}
+ if (!NoticeSourceEnum.SYSTEM.equals(notice.getSource()) && !notice.getOrganId().equals(OrganContextHolder.getOrganId())) {
+ throw ServiceExceptionUtil.exception(ErrorCodeConstants.NOTICE_NOT_FOUND);
+ }
+ // 只有超管可以操作内置公告
+ if (NoticeSourceEnum.SYSTEM.equals(notice.getSource()) && !SecurityFrameworkUtils.isSuperAdmin()) {
+ throw ServiceExceptionUtil.exception(ErrorCodeConstants.NOTICE_BUILDIN_MODIFY_PERMISSION_ERROR);
+ }
}
/**
@@ -84,14 +111,35 @@ public class NoticeServiceImpl implements NoticeService {
*
* @param reqVO
*/
+ @OrganIgnore
public void validateNameExists(NoticeSaveReqVO reqVO) {
+ boolean isSuperAdmin = SecurityFrameworkUtils.isSuperAdmin();
+
Long noticeId = reqVO.getId();
LambdaQueryWrapper wrapper = new LambdaQueryWrapperX().eq(NoticeDO::getTitle, reqVO.getTitle());
if (ObjectUtil.isNotNull(noticeId)) {
wrapper.ne(NoticeDO::getId, noticeId);
}
+ if (isSuperAdmin) {
+ wrapper.eq(NoticeDO::getSource, NoticeSourceEnum.SYSTEM);
+ } else {
+ wrapper.eq(NoticeDO::getOrganId, OrganContextHolder.getOrganId());
+ }
if (noticeMapper.exists(wrapper)) {
throw exception(NOTICE_NAME_UNIQE_ERROR);
}
}
+
+ /**
+ * 公告来源赋值
+ *
+ * @param notice
+ */
+ private void modifySource(NoticeDO notice) {
+ if (SecurityFrameworkUtils.isSuperAdmin()) {
+ notice.setSource(NoticeSourceEnum.SYSTEM);
+ } else {
+ notice.setSource(NoticeSourceEnum.CUSTOM);
+ }
+ }
}