0
0

PermissionService.cs 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Threading.Tasks;
  5. using Microsoft.Extensions.DependencyInjection;
  6. using ZhonTai.Admin.Core.Attributes;
  7. using ZhonTai.Admin.Core.Configs;
  8. using ZhonTai.Admin.Core.Dto;
  9. using ZhonTai.Admin.Services.Permission.Dto;
  10. using ZhonTai.Admin.Domain.Permission;
  11. using ZhonTai.Admin.Domain.RolePermission;
  12. using ZhonTai.Admin.Domain.TenantPermission;
  13. using ZhonTai.Admin.Domain.UserRole;
  14. using ZhonTai.Admin.Domain.PermissionApi;
  15. using ZhonTai.Admin.Domain.Role;
  16. using ZhonTai.Admin.Domain.User;
  17. using ZhonTai.DynamicApi;
  18. using ZhonTai.DynamicApi.Attributes;
  19. using ZhonTai.Admin.Core.Consts;
  20. using FreeSql;
  21. using ZhonTai.Admin.Domain.Tenant;
  22. namespace ZhonTai.Admin.Services.Permission;
  23. /// <summary>
  24. /// 权限服务
  25. /// </summary>
  26. [DynamicApi(Area = AdminConsts.AreaName)]
  27. public class PermissionService : BaseService, IPermissionService, IDynamicApi
  28. {
  29. private AppConfig _appConfig => LazyGetRequiredService<AppConfig>();
  30. private IPermissionRepository _permissionRepository => LazyGetRequiredService<IPermissionRepository>();
  31. private IRoleRepository _roleRepository => LazyGetRequiredService<IRoleRepository>();
  32. private IUserRepository _userRepository => LazyGetRequiredService<IUserRepository>();
  33. private IRolePermissionRepository _rolePermissionRepository => LazyGetRequiredService<IRolePermissionRepository>();
  34. private ITenantPermissionRepository _tenantPermissionRepository => LazyGetRequiredService<ITenantPermissionRepository>();
  35. private IUserRoleRepository _userRoleRepository => LazyGetRequiredService<IUserRoleRepository>();
  36. private IPermissionApiRepository _permissionApiRepository => LazyGetRequiredService<IPermissionApiRepository>();
  37. public PermissionService()
  38. {
  39. }
  40. /// <summary>
  41. /// 清除权限下关联的用户权限缓存
  42. /// </summary>
  43. /// <param name="permissionIds"></param>
  44. /// <returns></returns>
  45. private async Task ClearUserPermissionsAsync(List<long> permissionIds)
  46. {
  47. var userIds = await _userRoleRepository.Select.Where(a =>
  48. _rolePermissionRepository
  49. .Where(b => b.RoleId == a.RoleId && permissionIds.Contains(b.PermissionId))
  50. .Any()
  51. ).ToListAsync(a => a.UserId);
  52. foreach (var userId in userIds)
  53. {
  54. await Cache.DelAsync(CacheKeys.UserPermissions + userId);
  55. }
  56. }
  57. /// <summary>
  58. /// 查询分组
  59. /// </summary>
  60. /// <param name="id"></param>
  61. /// <returns></returns>
  62. public async Task<PermissionGetGroupOutput> GetGroupAsync(long id)
  63. {
  64. var result = await _permissionRepository.GetAsync<PermissionGetGroupOutput>(id);
  65. return result;
  66. }
  67. /// <summary>
  68. /// 查询菜单
  69. /// </summary>
  70. /// <param name="id"></param>
  71. /// <returns></returns>
  72. public async Task<PermissionGetMenuOutput> GetMenuAsync(long id)
  73. {
  74. var result = await _permissionRepository.GetAsync<PermissionGetMenuOutput>(id);
  75. return result;
  76. }
  77. /// <summary>
  78. /// 查询接口
  79. /// </summary>
  80. /// <param name="id"></param>
  81. /// <returns></returns>
  82. public async Task<PermissionGetApiOutput> GetApiAsync(long id)
  83. {
  84. var result = await _permissionRepository.GetAsync<PermissionGetApiOutput>(id);
  85. return result;
  86. }
  87. /// <summary>
  88. /// 查询权限点
  89. /// </summary>
  90. /// <param name="id"></param>
  91. /// <returns></returns>
  92. public async Task<PermissionGetDotOutput> GetDotAsync(long id)
  93. {
  94. var output = await _permissionRepository.Select
  95. .WhereDynamic(id)
  96. .ToOneAsync(a => new PermissionGetDotOutput
  97. {
  98. ApiIds = _permissionApiRepository.Where(b => b.PermissionId == a.Id).OrderBy(a => a.Id).ToList(b => b.Api.Id)
  99. });
  100. return output;
  101. }
  102. /// <summary>
  103. /// 查询权限列表
  104. /// </summary>
  105. /// <param name="key"></param>
  106. /// <param name="start"></param>
  107. /// <param name="end"></param>
  108. /// <returns></returns>
  109. public async Task<List<PermissionListOutput>> GetListAsync(string key, DateTime? start, DateTime? end)
  110. {
  111. if (end.HasValue)
  112. {
  113. end = end.Value.AddDays(1);
  114. }
  115. var data = await _permissionRepository
  116. .WhereIf(key.NotNull(), a => a.Path.Contains(key) || a.Label.Contains(key))
  117. .WhereIf(start.HasValue && end.HasValue, a => a.CreatedTime.Value.BetweenEnd(start.Value, end.Value))
  118. .Include(a => a.View)
  119. .OrderBy(a => new { a.ParentId, a.Sort })
  120. .ToListAsync(a=> new PermissionListOutput
  121. {
  122. ViewPath = a.View.Path,
  123. ApiPaths = string.Join(";", _permissionApiRepository.Where(b=>b.PermissionId == a.Id).ToList(b => b.Api.Path))
  124. });
  125. return data;
  126. }
  127. /// <summary>
  128. /// 查询角色权限-权限列表
  129. /// </summary>
  130. /// <returns></returns>
  131. public async Task<IEnumerable<dynamic>> GetPermissionList()
  132. {
  133. var permissions = await _permissionRepository.Select
  134. .WhereIf(_appConfig.Tenant && User.TenantType == TenantType.Tenant, a =>
  135. _tenantPermissionRepository
  136. .Where(b => b.PermissionId == a.Id && b.TenantId == User.TenantId)
  137. .Any()
  138. )
  139. .AsTreeCte(up: true)
  140. .ToListAsync(a => new { a.Id, a.ParentId, a.Label, a.Type, a.Sort });
  141. var menus = permissions.DistinctBy(a => a.Id).OrderBy(a => a.ParentId).ThenBy(a => a.Sort)
  142. .Select(a => new
  143. {
  144. a.Id,
  145. a.ParentId,
  146. a.Label,
  147. Row = a.Type == PermissionType.Menu
  148. });
  149. return menus;
  150. }
  151. /// <summary>
  152. /// 查询角色权限列表
  153. /// </summary>
  154. /// <param name="roleId"></param>
  155. /// <returns></returns>
  156. public async Task<List<long>> GetRolePermissionList(long roleId = 0)
  157. {
  158. var permissionIds = await _rolePermissionRepository
  159. .Select.Where(d => d.RoleId == roleId)
  160. .ToListAsync(a => a.PermissionId);
  161. return permissionIds;
  162. }
  163. /// <summary>
  164. /// 查询租户权限列表
  165. /// </summary>
  166. /// <param name="tenantId"></param>
  167. /// <returns></returns>
  168. public async Task<List<long>> GetTenantPermissionList(long tenantId)
  169. {
  170. var permissionIds = await _tenantPermissionRepository
  171. .Select.Where(d => d.TenantId == tenantId)
  172. .ToListAsync(a => a.PermissionId);
  173. return permissionIds;
  174. }
  175. /// <summary>
  176. /// 新增分组
  177. /// </summary>
  178. /// <param name="input"></param>
  179. /// <returns></returns>
  180. public async Task<long> AddGroupAsync(PermissionAddGroupInput input)
  181. {
  182. var entity = Mapper.Map<PermissionEntity>(input);
  183. entity.Type = PermissionType.Group;
  184. if (entity.Sort == 0)
  185. {
  186. var sort = await _permissionRepository.Select.Where(a => a.ParentId == input.ParentId).MaxAsync(a => a.Sort);
  187. entity.Sort = sort + 1;
  188. }
  189. await _permissionRepository.InsertAsync(entity);
  190. return entity.Id;
  191. }
  192. /// <summary>
  193. /// 新增菜单
  194. /// </summary>
  195. /// <param name="input"></param>
  196. /// <returns></returns>
  197. public async Task<long> AddMenuAsync(PermissionAddMenuInput input)
  198. {
  199. var entity = Mapper.Map<PermissionEntity>(input);
  200. entity.Type = PermissionType.Menu;
  201. if (entity.Sort == 0)
  202. {
  203. var sort = await _permissionRepository.Select.Where(a => a.ParentId == input.ParentId).MaxAsync(a => a.Sort);
  204. entity.Sort = sort + 1;
  205. }
  206. await _permissionRepository.InsertAsync(entity);
  207. return entity.Id;
  208. }
  209. /// <summary>
  210. /// 新增接口
  211. /// </summary>
  212. /// <param name="input"></param>
  213. /// <returns></returns>
  214. public async Task<long> AddApiAsync(PermissionAddApiInput input)
  215. {
  216. var entity = Mapper.Map<PermissionEntity>(input);
  217. entity.Type = PermissionType.Dot;
  218. if (entity.Sort == 0)
  219. {
  220. var sort = await _permissionRepository.Select.Where(a => a.ParentId == input.ParentId).MaxAsync(a => a.Sort);
  221. entity.Sort = sort + 1;
  222. }
  223. await _permissionRepository.InsertAsync(entity);
  224. return entity.Id;
  225. }
  226. /// <summary>
  227. /// 新增权限点
  228. /// </summary>
  229. /// <param name="input"></param>
  230. /// <returns></returns>
  231. [AdminTransaction]
  232. public virtual async Task<long> AddDotAsync(PermissionAddDotInput input)
  233. {
  234. var entity = Mapper.Map<PermissionEntity>(input);
  235. entity.Type = PermissionType.Dot;
  236. if (entity.Sort == 0)
  237. {
  238. var sort = await _permissionRepository.Select.Where(a => a.ParentId == input.ParentId).MaxAsync(a => a.Sort);
  239. entity.Sort = sort + 1;
  240. }
  241. await _permissionRepository.InsertAsync(entity);
  242. if (input.ApiIds != null && input.ApiIds.Any())
  243. {
  244. var permissionApis = input.ApiIds.Select(a => new PermissionApiEntity { PermissionId = entity.Id, ApiId = a });
  245. await _permissionApiRepository.InsertAsync(permissionApis);
  246. }
  247. return entity.Id;
  248. }
  249. /// <summary>
  250. /// 修改分组
  251. /// </summary>
  252. /// <param name="input"></param>
  253. /// <returns></returns>
  254. public async Task UpdateGroupAsync(PermissionUpdateGroupInput input)
  255. {
  256. var entity = await _permissionRepository.GetAsync(input.Id);
  257. entity = Mapper.Map(input, entity);
  258. await _permissionRepository.UpdateAsync(entity);
  259. }
  260. /// <summary>
  261. /// 修改菜单
  262. /// </summary>
  263. /// <param name="input"></param>
  264. /// <returns></returns>
  265. public async Task UpdateMenuAsync(PermissionUpdateMenuInput input)
  266. {
  267. var entity = await _permissionRepository.GetAsync(input.Id);
  268. entity = Mapper.Map(input, entity);
  269. await _permissionRepository.UpdateAsync(entity);
  270. }
  271. /// <summary>
  272. /// 修改接口
  273. /// </summary>
  274. /// <param name="input"></param>
  275. /// <returns></returns>
  276. public async Task UpdateApiAsync(PermissionUpdateApiInput input)
  277. {
  278. var entity = await _permissionRepository.GetAsync(input.Id);
  279. entity = Mapper.Map(input, entity);
  280. await _permissionRepository.UpdateAsync(entity);
  281. }
  282. /// <summary>
  283. /// 修改权限点
  284. /// </summary>
  285. /// <param name="input"></param>
  286. /// <returns></returns>
  287. [AdminTransaction]
  288. public virtual async Task UpdateDotAsync(PermissionUpdateDotInput input)
  289. {
  290. var entity = await _permissionRepository.GetAsync(input.Id);
  291. if (!(entity?.Id > 0))
  292. {
  293. throw ResultOutput.Exception("权限点不存在!");
  294. }
  295. Mapper.Map(input, entity);
  296. await _permissionRepository.UpdateAsync(entity);
  297. await _permissionApiRepository.DeleteAsync(a => a.PermissionId == entity.Id);
  298. if (input.ApiIds != null && input.ApiIds.Any())
  299. {
  300. var permissionApis = input.ApiIds.Select(a => new PermissionApiEntity { PermissionId = entity.Id, ApiId = a });
  301. await _permissionApiRepository.InsertAsync(permissionApis.ToList());
  302. }
  303. //清除用户权限缓存
  304. await ClearUserPermissionsAsync(new List<long> { entity.Id });
  305. }
  306. /// <summary>
  307. /// 彻底删除
  308. /// </summary>
  309. /// <param name="id"></param>
  310. /// <returns></returns>
  311. [AdminTransaction]
  312. public virtual async Task DeleteAsync(long id)
  313. {
  314. //递归查询所有权限点
  315. var ids = _permissionRepository.Select
  316. .Where(a => a.Id == id)
  317. .AsTreeCte()
  318. .ToList(a => a.Id);
  319. //删除权限关联接口
  320. await _permissionApiRepository.DeleteAsync(a => ids.Contains(a.PermissionId));
  321. //删除相关权限
  322. await _permissionRepository.DeleteAsync(a => ids.Contains(a.Id));
  323. //清除用户权限缓存
  324. await ClearUserPermissionsAsync(ids);
  325. }
  326. /// <summary>
  327. /// 删除
  328. /// </summary>
  329. /// <param name="id"></param>
  330. /// <returns></returns>
  331. public async Task SoftDeleteAsync(long id)
  332. {
  333. //递归查询所有权限点
  334. var ids = _permissionRepository.Select
  335. .Where(a => a.Id == id)
  336. .AsTreeCte()
  337. .ToList(a => a.Id);
  338. //删除权限
  339. await _permissionRepository.SoftDeleteAsync(a => ids.Contains(a.Id));
  340. //清除用户权限缓存
  341. await ClearUserPermissionsAsync(ids);
  342. }
  343. /// <summary>
  344. /// 保存角色权限
  345. /// </summary>
  346. /// <param name="input"></param>
  347. /// <returns></returns>
  348. [AdminTransaction]
  349. public virtual async Task AssignAsync(PermissionAssignInput input)
  350. {
  351. //分配权限的时候判断角色是否存在
  352. var exists = await _roleRepository.Select.DisableGlobalFilter(FilterNames.Tenant).WhereDynamic(input.RoleId).AnyAsync();
  353. if (!exists)
  354. {
  355. throw ResultOutput.Exception("该角色不存在或已被删除!");
  356. }
  357. //查询角色权限
  358. var permissionIds = await _rolePermissionRepository.Select.Where(d => d.RoleId == input.RoleId).ToListAsync(m => m.PermissionId);
  359. //批量删除权限
  360. var deleteIds = permissionIds.Where(d => !input.PermissionIds.Contains(d));
  361. if (deleteIds.Any())
  362. {
  363. await _rolePermissionRepository.DeleteAsync(m => m.RoleId == input.RoleId && deleteIds.Contains(m.PermissionId));
  364. }
  365. //批量插入权限
  366. var insertRolePermissions = new List<RolePermissionEntity>();
  367. var insertPermissionIds = input.PermissionIds.Where(d => !permissionIds.Contains(d));
  368. //防止租户非法授权,查询主库租户权限范围
  369. if (_appConfig.Tenant && User.TenantType == TenantType.Tenant)
  370. {
  371. var cloud = ServiceProvider.GetRequiredService<FreeSqlCloud>();
  372. var tenantPermissionIds = await cloud.Use(DbKeys.AppDb).Select<TenantPermissionEntity>().Where(d => d.TenantId == User.TenantId).ToListAsync(m => m.PermissionId);
  373. insertPermissionIds = insertPermissionIds.Where(d => tenantPermissionIds.Contains(d));
  374. }
  375. if (insertPermissionIds.Any())
  376. {
  377. foreach (var permissionId in insertPermissionIds)
  378. {
  379. insertRolePermissions.Add(new RolePermissionEntity()
  380. {
  381. RoleId = input.RoleId,
  382. PermissionId = permissionId,
  383. });
  384. }
  385. await _rolePermissionRepository.InsertAsync(insertRolePermissions);
  386. }
  387. //清除角色下关联的用户权限缓存
  388. var userIds = await _userRoleRepository.Select.Where(a => a.RoleId == input.RoleId).ToListAsync(a => a.UserId);
  389. foreach (var userId in userIds)
  390. {
  391. await Cache.DelAsync(CacheKeys.UserPermissions + userId);
  392. }
  393. }
  394. /// <summary>
  395. /// 保存租户权限
  396. /// </summary>
  397. /// <param name="input"></param>
  398. /// <returns></returns>
  399. [AdminTransaction]
  400. public virtual async Task SaveTenantPermissionsAsync(PermissionSaveTenantPermissionsInput input)
  401. {
  402. //查询租户权限
  403. var permissionIds = await _tenantPermissionRepository.Select.Where(d => d.TenantId == input.TenantId).ToListAsync(m => m.PermissionId);
  404. //批量删除租户权限
  405. var deleteIds = permissionIds.Where(d => !input.PermissionIds.Contains(d));
  406. if (deleteIds.Any())
  407. {
  408. await _tenantPermissionRepository.DeleteAsync(m => m.TenantId == input.TenantId && deleteIds.Contains(m.PermissionId));
  409. //删除租户下关联的角色权限
  410. await _rolePermissionRepository.DeleteAsync(a => deleteIds.Contains(a.PermissionId));
  411. }
  412. //批量插入租户权限
  413. var tenatPermissions = new List<TenantPermissionEntity>();
  414. var insertPermissionIds = input.PermissionIds.Where(d => !permissionIds.Contains(d));
  415. if (insertPermissionIds.Any())
  416. {
  417. foreach (var permissionId in insertPermissionIds)
  418. {
  419. tenatPermissions.Add(new TenantPermissionEntity()
  420. {
  421. TenantId = input.TenantId,
  422. PermissionId = permissionId,
  423. });
  424. }
  425. await _tenantPermissionRepository.InsertAsync(tenatPermissions);
  426. }
  427. //清除租户下所有用户权限缓存
  428. var userIds = await _userRepository.Select.Where(a => a.TenantId == input.TenantId).ToListAsync(a => a.Id);
  429. if(userIds.Any())
  430. {
  431. foreach (var userId in userIds)
  432. {
  433. await Cache.DelAsync(CacheKeys.UserPermissions + userId);
  434. }
  435. }
  436. }
  437. }