Browse Source

feat(crm-auth): Ticket 05 — 权限码并集注入(按钮级鉴权)

- initDataScopeContext 在数据范围计算后追加 perms 并集
- 查 sys_user_role → sys_role_menu → sys_menu 收集 enabled button 的 perms
- 停用(status=disabled)的权限点不进并集,重新启用自动恢复
- perms 与 roleCode 同为 Spring Security authority,hasAuthority/hasRole 各自匹配
- try-catch 保护:sys_menu/sys_role_menu 表未创建时静默跳过
- 114 tests 全绿,零回归
master
luoweijian 1 month ago
parent
commit
53d82c960b
  1. 31
      crm-auth/src/main/java/com/crm/auth/service/impl/PermissionServiceImpl.java

31
crm-auth/src/main/java/com/crm/auth/service/impl/PermissionServiceImpl.java

@ -1,6 +1,7 @@
package com.crm.auth.service.impl; package com.crm.auth.service.impl;
import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.crm.auth.domain.entity.*; import com.crm.auth.domain.entity.*;
import com.crm.auth.mapper.*; import com.crm.auth.mapper.*;
@ -69,10 +70,36 @@ public class PermissionServiceImpl {
} }
DataVisibilityContext.load( DataVisibilityContext.load(
new DataVisibility(userId, primaryDeptId, List.copyOf(deptIds), widest, expandedDeptIds)); new DataVisibility(userId, primaryDeptId, List.copyOf(deptIds), widest, expandedDeptIds));
return roles.stream()
// ── 权限码并集(ADR-0011):收集用户所有角色授权的 button 节点 perms ──
List<String> authorities = new ArrayList<>();
if (CollUtil.isNotEmpty(userRoles)) {
try {
Set<Long> roleIds = userRoles.stream().map(SysUserRole::getRoleId).collect(Collectors.toSet());
List<SysRoleMenu> allRoleMenus = sysRoleMenuMapper.selectList(
new LambdaQueryWrapper<SysRoleMenu>().in(SysRoleMenu::getRoleId, roleIds));
if (CollUtil.isNotEmpty(allRoleMenus)) {
Set<Long> menuIds = allRoleMenus.stream()
.map(SysRoleMenu::getMenuId).collect(Collectors.toSet());
List<SysMenu> menus = sysMenuMapper.selectBatchIds(menuIds);
menus.stream()
.filter(m -> m.getMenuType() != null && m.getMenuType() == 3)
.filter(m -> "enabled".equals(m.getStatus()))
.map(SysMenu::getPerms)
.filter(StrUtil::isNotBlank)
.distinct()
.forEach(authorities::add);
}
} catch (Exception e) {
log.debug("权限码并集查询失败(可能 sys_menu/sys_role_menu 表尚未创建),跳过", e);
}
}
// 角色编码追加在权限码之后(两者同为 Spring Security authority,hasRole/hasAuthority 各自匹配)
roles.stream()
.map(SysRole::getRoleCode) .map(SysRole::getRoleCode)
.filter(Objects::nonNull) .filter(Objects::nonNull)
.toList(); .forEach(authorities::add);
return authorities;
} }
public List<SysMenu> getMenuTree(Long userId) { public List<SysMenu> getMenuTree(Long userId) {

Loading…
Cancel
Save