SystemRoleMenuServiceImpl.java
6.12 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
package com.diligrp.rider.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.diligrp.rider.common.enums.AdminRoleScopeEnum;
import com.diligrp.rider.common.enums.MenuScopeEnum;
import com.diligrp.rider.common.exception.BizException;
import com.diligrp.rider.dto.AdminRoleMenuAssignDTO;
import com.diligrp.rider.entity.SysMenu;
import com.diligrp.rider.entity.SysRole;
import com.diligrp.rider.entity.SysRoleMenu;
import com.diligrp.rider.mapper.SysRoleMapper;
import com.diligrp.rider.mapper.SysRoleMenuMapper;
import com.diligrp.rider.service.SystemRoleMenuService;
import com.diligrp.rider.vo.AdminRoleMenuTreeVO;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
@Service
@RequiredArgsConstructor
public class SystemRoleMenuServiceImpl implements SystemRoleMenuService {
private final SysRoleMapper sysRoleMapper;
private final SysRoleMenuMapper sysRoleMenuMapper;
private final SystemMenuServiceImpl systemMenuService;
// ----------------------------------------------------------------
// 平台侧:不限菜单 scope(平台管理员可分配所有菜单)
// ----------------------------------------------------------------
@Override
public List<AdminRoleMenuTreeVO> getRoleMenuTree(Long roleId) {
SysRole role = requireRole(roleId, null);
List<SysMenu> allowedMenus = filterMenusByScope(systemMenuService.listAllMenus(), role);
return buildCheckedTree(roleId, allowedMenus);
}
@Override
@Transactional
public void assignMenus(Long roleId, AdminRoleMenuAssignDTO dto) {
SysRole role = requireRole(roleId, null);
List<SysMenu> allowedMenus = filterMenusByScope(systemMenuService.listAllMenus(), role);
doAssignMenus(roleId, dto, allowedMenus);
}
// ----------------------------------------------------------------
// 分站侧:仅允许 SUBSTATION / BOTH scope 的菜单,且校验角色归属 cityId
// ----------------------------------------------------------------
public List<AdminRoleMenuTreeVO> getRoleMenuTreeForCity(Long roleId, Long cityId) {
SysRole role = requireRole(roleId, cityId);
List<SysMenu> allowedMenus = filterSubstationMenus(systemMenuService.listAllMenus());
return buildCheckedTree(roleId, allowedMenus);
}
@Transactional
public void assignMenusForCity(Long roleId, AdminRoleMenuAssignDTO dto, Long cityId) {
SysRole role = requireRole(roleId, cityId);
List<SysMenu> allowedMenus = filterSubstationMenus(systemMenuService.listAllMenus());
doAssignMenus(roleId, dto, allowedMenus);
}
// ----------------------------------------------------------------
// 私有工具
// ----------------------------------------------------------------
private List<AdminRoleMenuTreeVO> buildCheckedTree(Long roleId, List<SysMenu> allowedMenus) {
List<SysRoleMenu> assigned = sysRoleMenuMapper.selectList(new LambdaQueryWrapper<SysRoleMenu>()
.eq(SysRoleMenu::getRoleId, roleId));
Set<Long> assignedIds = assigned.stream().map(SysRoleMenu::getMenuId).collect(Collectors.toSet());
Map<Long, Boolean> checkedMap = new LinkedHashMap<>();
for (SysMenu menu : allowedMenus) {
checkedMap.put(menu.getId(), assignedIds.contains(menu.getId()));
}
return systemMenuService.buildTree(allowedMenus, checkedMap, false);
}
private void doAssignMenus(Long roleId, AdminRoleMenuAssignDTO dto, List<SysMenu> allowedMenus) {
Set<Long> allowedIds = allowedMenus.stream().map(SysMenu::getId).collect(Collectors.toSet());
List<Long> menuIds = dto.getMenuIds() == null ? List.of() : dto.getMenuIds();
for (Long menuId : menuIds) {
if (!allowedIds.contains(menuId)) {
throw new BizException("存在不允许分配的菜单");
}
}
sysRoleMenuMapper.delete(new LambdaQueryWrapper<SysRoleMenu>()
.eq(SysRoleMenu::getRoleId, roleId));
long now = System.currentTimeMillis() / 1000;
for (Long menuId : menuIds) {
SysRoleMenu roleMenu = new SysRoleMenu();
roleMenu.setRoleId(roleId);
roleMenu.setMenuId(menuId);
roleMenu.setCreateTime(now);
sysRoleMenuMapper.insert(roleMenu);
}
}
private SysRole requireRole(Long roleId, Long cityId) {
SysRole role = sysRoleMapper.selectById(roleId);
if (role == null || role.getStatus() == null || role.getStatus() != 1) {
throw new BizException("角色不存在或已禁用");
}
// cityId != null 时校验归属(分站侧调用)
if (cityId != null && !cityId.equals(role.getCityId())) {
throw new BizException("无权操作其他租户的角色");
}
return role;
}
private List<SysMenu> filterMenusByScope(List<SysMenu> menus, SysRole role) {
return menus.stream().filter(menu -> isScopeAllowed(role, menu)).collect(Collectors.toList());
}
/** 分站侧:只允许 SUBSTATION 或 BOTH scope 的菜单 */
private List<SysMenu> filterSubstationMenus(List<SysMenu> menus) {
return menus.stream().filter(menu ->
MenuScopeEnum.SUBSTATION.name().equals(menu.getMenuScope())
|| MenuScopeEnum.BOTH.name().equals(menu.getMenuScope())
).collect(Collectors.toList());
}
private boolean isScopeAllowed(SysRole role, SysMenu menu) {
if (MenuScopeEnum.BOTH.name().equals(menu.getMenuScope())) {
return true;
}
if (AdminRoleScopeEnum.PLATFORM.name().equals(role.getRoleScope())) {
return MenuScopeEnum.PLATFORM.name().equals(menu.getMenuScope());
}
if (AdminRoleScopeEnum.SUBSTATION.name().equals(role.getRoleScope())) {
return MenuScopeEnum.SUBSTATION.name().equals(menu.getMenuScope());
}
return false;
}
}