diff --git a/Src/Dlhis.Basic/Device/Controllers/DevicePermissionsController.cs b/Src/Dlhis.Basic/Device/Controllers/DevicePermissionsController.cs index d42822b9..0e26e4f6 100644 --- a/Src/Dlhis.Basic/Device/Controllers/DevicePermissionsController.cs +++ b/Src/Dlhis.Basic/Device/Controllers/DevicePermissionsController.cs @@ -1,5 +1,4 @@ -using Dlhis.Basic.Device.Dtos; -using Dlhis.Basic.Device.Filters; +using Dlhis.Basic.Device.Filters; using Dlhis.Basic.Device.Request; using Dlhis.Basic.Device.Response; using Dlhis.Basic.Device.Services; @@ -108,12 +107,4 @@ public class DevicePermissionsController : ControllerBase { return await _devicePermissionService.GetAssignDeviceCodesAsync(userCode); } - - [AllowAnonymous] - [HttpGet("test")] - [IgnoreTenant] - public async Task>> GetUserDevicePermissionsAsync(string code) - { - return await _devicePermissionService.GetUserDevicePermissionsAsync(code); - } } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Dtos/PermissionUsersInfoDto.cs b/Src/Dlhis.Basic/Device/Dtos/PermissionUsersInfoDto.cs deleted file mode 100644 index ac59afd3..00000000 --- a/Src/Dlhis.Basic/Device/Dtos/PermissionUsersInfoDto.cs +++ /dev/null @@ -1,15 +0,0 @@ -namespace Dlhis.Basic.Device.Dtos -{ - public class PermissionUsersInfoDto - { - /// - /// 拥有权限的用户 - /// - public List UserNos { get; set; } - - /// - /// 用户对应的 [ 厂区--设备Code ] - /// - public Dictionary> PermissionInfos { get; set; } - } -} diff --git a/Src/Dlhis.Basic/Device/Dtos/UserTenantDeviceCodeDto.cs b/Src/Dlhis.Basic/Device/Dtos/TenantAssignTypeDeviceCode.cs similarity index 72% rename from Src/Dlhis.Basic/Device/Dtos/UserTenantDeviceCodeDto.cs rename to Src/Dlhis.Basic/Device/Dtos/TenantAssignTypeDeviceCode.cs index 52065902..19760256 100644 --- a/Src/Dlhis.Basic/Device/Dtos/UserTenantDeviceCodeDto.cs +++ b/Src/Dlhis.Basic/Device/Dtos/TenantAssignTypeDeviceCode.cs @@ -2,6 +2,35 @@ namespace Dlhis.Basic.Device.Dtos; +/// +/// 厂区对应分配类型的设备权限 +/// +public class TenantAssignTypeDeviceCode +{ + /// + /// 租户 + /// + public string Tenant { get; set; } + + /// + /// 设备权限 + /// + public IEnumerable AssignTypes { get; init; } +} + +public class AssignTypeDeviceCode +{ + /// + /// 分配类型 + /// + public AssignTypeEnumType AssignType { get; init; } + + /// + /// 设备权限 + /// + public IEnumerable Codes { get; init; } +} + public class UserTenantDeviceCodeDto { /// @@ -9,32 +38,6 @@ public class UserTenantDeviceCodeDto /// public string Tenant { get; set; } - /// - /// 设备权限 - /// - public IEnumerable Codes { get; set; } -} - -public class TenantAssignTypeDeviceCode -{ - /// - /// 租户 - /// - public string Tenant { get; set; } - - /// - /// 设备权限 - /// - public IEnumerable Codes { get; set; } -} - -public class AssignTypeDeviceCode -{ - /// - /// 分配类型 - /// - public AssignTypeEnumType AssignType { get; set; } - /// /// 设备权限 /// diff --git a/Src/Dlhis.Basic/Device/Filters/AssignPermissionLimitAttribute.cs b/Src/Dlhis.Basic/Device/Filters/AssignPermissionLimitAttribute.cs index fa96d0d8..9f4d637b 100644 --- a/Src/Dlhis.Basic/Device/Filters/AssignPermissionLimitAttribute.cs +++ b/Src/Dlhis.Basic/Device/Filters/AssignPermissionLimitAttribute.cs @@ -1,5 +1,5 @@ using Kurisu.AspNetCore.Authentication.Abstractions; -using Kurisu.AspNetCore.Utils; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.Utils.Extensions; using Microsoft.AspNetCore.Mvc.Filters; @@ -11,12 +11,11 @@ public class AssignPermissionLimitAttribute : Attribute, IAsyncActionFilter public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next) { var currentUser = context.HttpContext.RequestServices.GetRequiredService(); - //var userId = currentUser.GetIntSubjectId(); var redisCache = context.HttpContext.RequestServices.GetRequiredService(); var currentTenantId = currentUser.GetStringTenantId(); - await using var handler = await redisCache.LockAsync($"permission:generate:{currentTenantId}"); + await using var handler = await redisCache.LockAsync($"permission:generate:{currentTenantId}", expiry: TimeSpan.FromMinutes(3)); handler.Acquired.ThrowIfFalse("请勿频繁分配"); await next(); } diff --git a/Src/Dlhis.Basic/Device/PermissionAnalyzeConstants.cs b/Src/Dlhis.Basic/Device/PermissionAnalyzeConstants.cs index 6f0e1221..2232d201 100644 --- a/Src/Dlhis.Basic/Device/PermissionAnalyzeConstants.cs +++ b/Src/Dlhis.Basic/Device/PermissionAnalyzeConstants.cs @@ -2,7 +2,7 @@ using Dlhis.Entity.Sys.Enums; namespace Dlhis.Basic.Device; -public class PermissionAnalyzeConstants +public static class PermissionAnalyzeConstants { private const string _verb = "PermissionAnalyze"; public const string User = nameof(AssignTypeEnumType.User) + _verb; @@ -10,7 +10,6 @@ public class PermissionAnalyzeConstants public const string Department = nameof(AssignTypeEnumType.Department) + _verb; public const string Tenant = nameof(AssignTypeEnumType.Tenant) + _verb; - public static string GetTypeName(AssignTypeEnumType assignTypeEnumType) { return assignTypeEnumType + _verb; diff --git a/Src/Dlhis.Basic/Device/Request/DeviceAssignRequest.cs b/Src/Dlhis.Basic/Device/Request/DeviceAssignRequest.cs index 3a6be64f..a04dd833 100644 --- a/Src/Dlhis.Basic/Device/Request/DeviceAssignRequest.cs +++ b/Src/Dlhis.Basic/Device/Request/DeviceAssignRequest.cs @@ -13,5 +13,5 @@ public class DeviceAssignRequest /// /// 设备code /// - public List DeviceCodes { get; set; } = new List(); + public List DeviceCodes { get; set; } = new(); } diff --git a/Src/Dlhis.Basic/Device/Request/DevicePermissionSaveRequest.cs b/Src/Dlhis.Basic/Device/Request/DevicePermissionSaveRequest.cs index 067b7d5f..c47e060c 100644 --- a/Src/Dlhis.Basic/Device/Request/DevicePermissionSaveRequest.cs +++ b/Src/Dlhis.Basic/Device/Request/DevicePermissionSaveRequest.cs @@ -61,4 +61,13 @@ public class DevicePermissionSaveRequest : IValidatableObject yield return new ValidationResult("暂不支持角色分配", new[] { nameof(AssignType) }); } } + + /// + /// 获取实际分配的权限值 + /// + /// + public string GetActualAssignValue() + { + return AssignType == AssignTypeEnumType.Department ? TenantId + ":" + AssignValue : AssignValue; + } } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Response/DevicePermissionAssignResponse.cs b/Src/Dlhis.Basic/Device/Response/DevicePermissionAssignResponse.cs index 01c0585a..79f8bdab 100644 --- a/Src/Dlhis.Basic/Device/Response/DevicePermissionAssignResponse.cs +++ b/Src/Dlhis.Basic/Device/Response/DevicePermissionAssignResponse.cs @@ -2,6 +2,12 @@ namespace Dlhis.Basic.Device.Response; public class DevicePermissionAssignResponse { + public DevicePermissionAssignResponse(int addCount, int deleteCount) + { + AddCount = addCount; + DeleteCount = deleteCount; + } + /// /// 添加数量 /// diff --git a/Src/Dlhis.Basic/Device/Services/IDevicePermissionAnalyzeService.cs b/Src/Dlhis.Basic/Device/Services/IDevicePermissionAnalyzeService.cs index 43b4ea4a..0c8e3a67 100644 --- a/Src/Dlhis.Basic/Device/Services/IDevicePermissionAnalyzeService.cs +++ b/Src/Dlhis.Basic/Device/Services/IDevicePermissionAnalyzeService.cs @@ -13,14 +13,11 @@ public interface IDevicePermissionAnalyzeService : IScopeDependency { Task GenerateDeviceTasksAsync(Func func, List userNos); - Task>> GetAssignDeviceCodesInternalAsync(List userNos); - - Task>> GetAssignDeviceCodesInternalAsync(List userNos, params AssignTypeEnumType[] ignoreAssignTypes); + Task>> GetUserAssignDeviceCodesWithTypeInTenantAsync(List userNos, params AssignTypeEnumType[] ignoreAssignTypes); Task> GetAssignmentsAsync(DeviceGetAssignmentsRequest request); Task> GetAssignmentUniqueAsync(DeviceGetAssignmentUniquesRequest request); - Task> GetAssignDeviceCodesAsync(string userCode); } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Services/IDevicePermissionService.cs b/Src/Dlhis.Basic/Device/Services/IDevicePermissionService.cs index 10ac7f8a..17b9d049 100644 --- a/Src/Dlhis.Basic/Device/Services/IDevicePermissionService.cs +++ b/Src/Dlhis.Basic/Device/Services/IDevicePermissionService.cs @@ -27,7 +27,7 @@ public interface IDevicePermissionService : IScopeDependency Task AssignToUniqueImportAsync(IFormFile file); - Task>> GetUserDevicePermissionsAsync(string code); + Task>> GetUserDevicePermissionsAsync(string code); /// /// 生成下发任务(主动生成) diff --git a/Src/Dlhis.Basic/Device/Services/IParallelService.cs b/Src/Dlhis.Basic/Device/Services/IParallelService.cs deleted file mode 100644 index 55f9471f..00000000 --- a/Src/Dlhis.Basic/Device/Services/IParallelService.cs +++ /dev/null @@ -1,6 +0,0 @@ -namespace Dlhis.Basic.Device.Services; - -public interface IParallelService : IScopeDependency -{ - public bool Enable { get; set; } -} \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Services/IPermissionAnalyzeService.cs b/Src/Dlhis.Basic/Device/Services/IPermissionAnalyzeService.cs index c2806f9e..e596cdce 100644 --- a/Src/Dlhis.Basic/Device/Services/IPermissionAnalyzeService.cs +++ b/Src/Dlhis.Basic/Device/Services/IPermissionAnalyzeService.cs @@ -1,8 +1,17 @@ using Dlhis.Basic.Device.Request; +using Dlhis.Basic.Device.Response; namespace Dlhis.Basic.Device.Services; +/// +/// 权限分析 +/// public interface IPermissionAnalyzeService { - Task AnalyzeAsync(DevicePermissionSaveRequest request); + /// + /// 分析操作 + /// + /// + /// + Task AnalyzeAsync(DevicePermissionSaveRequest request); } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Services/Implements/BasePermissionAnalyzeService.cs b/Src/Dlhis.Basic/Device/Services/Implements/BasePermissionAnalyzeService.cs index c48916ee..a2aabf0c 100644 --- a/Src/Dlhis.Basic/Device/Services/Implements/BasePermissionAnalyzeService.cs +++ b/Src/Dlhis.Basic/Device/Services/Implements/BasePermissionAnalyzeService.cs @@ -1,6 +1,7 @@ using Dlhis.Basic.DataPermissions; using Dlhis.Basic.Device.Dtos; using Dlhis.Basic.Device.Request; +using Dlhis.Basic.Device.Response; using Dlhis.Entity.Basic.Entity; using Dlhis.Entity.Device.Entities; using Dlhis.Entity.Device.Enums; @@ -15,50 +16,52 @@ using SqlSugar; namespace Dlhis.Basic.Device.Services.Implements; +/// +/// 权限分析基类 +/// public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService { private readonly ICurrentUser _currentUser; - private readonly IDevicePermissionAnalyzeService _devicePermissionAnalyzeService; private readonly IMyDataPermissionService _myDataPermissionService; + private readonly IDevicePermissionAnalyzeService _devicePermissionAnalyzeService; + protected IDbContext DbContext { get; } protected BasePermissionAnalyzeService(IServiceProvider serviceProvider) { _currentUser = serviceProvider.GetService(); - _devicePermissionAnalyzeService = serviceProvider.GetService(); _myDataPermissionService = serviceProvider.GetService(); DbContext = serviceProvider.GetService(); CurrentTenantId = _currentUser.GetStringTenantId(); + _devicePermissionAnalyzeService = serviceProvider.GetService(); } private string CurrentTenantId { get; } - public ISugarQueryable DevicePermission => DbContext.Queryable(); + protected ISugarQueryable DevicePermission => DbContext.Queryable(); - - public async Task AnalyzeAsync(DevicePermissionSaveRequest request) + public async Task AnalyzeAsync(DevicePermissionSaveRequest request) { - var currentAssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; - - await CheckAssignTopDoorDeviceGroupAsync(request); + await CheckWhetherAssignToTopDeviceGroupAsync(request); + await CheckAssignedToTenantAsync(request); var dps = await GetAssignedDevicePermissionsAsync(request); (List codesToAdd, List codesToDelete) = await GetDiffAsync(request.UniqueType, dps, request.Codes); if (codesToAdd.IsEmpty() && codesToDelete.IsEmpty()) { - return; + return new DevicePermissionAssignResponse(0, 0); } var devicesToAdd = await DbContext.Queryable().Where(x => codesToAdd.Contains(x.Code)).Distinct().ToListAsync(); var devicesToDelete = await DbContext.Queryable().Where(x => codesToDelete.Contains(x.Code)).Distinct().ToListAsync(); - var gainfoNos = await GetGainfoNosAsync(currentAssignValue); + var gainfoNos = await GetGainfoNosAsync(request.GetActualAssignValue()); var userTenantDeviceCodes = devicesToDelete.IsPresent() && request.AssignType != AssignTypeEnumType.Tenant - ? await _devicePermissionAnalyzeService.GetAssignDeviceCodesInternalAsync(gainfoNos, request.AssignType) - : new Dictionary>(); + ? await _devicePermissionAnalyzeService.GetUserAssignDeviceCodesWithTypeInTenantAsync(gainfoNos, request.AssignType) + : new Dictionary>(); var tasks = new List(); foreach (var gainfoNo in gainfoNos) @@ -81,7 +84,7 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService if (userTenantDeviceCodes.Any()) { - var myDeviceCodes = userTenantDeviceCodes[gainfoNo].SelectMany(x => x.Codes).SelectMany(x => x.Codes); + var myDeviceCodes = userTenantDeviceCodes[gainfoNo].SelectMany(x => x.AssignTypes).SelectMany(x => x.Codes); devicesToDelete = devicesToDelete.Where(p => devicesToDelete.Select(x => x.Code).Except(myDeviceCodes).Contains(p.Code)).ToList(); } @@ -104,13 +107,58 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService await ChunkInsertAsync(tasks); await PersistDataAsync(dps, request); + + return new DevicePermissionAssignResponse(devicesToAdd.Count, devicesToDelete.Count); } - private async Task ChunkInsertAsync(List batch) where T : class, new() + + public async Task CheckAssignedToTenantAsync(DevicePermissionSaveRequest request) { - foreach (var tasks in batch.Chunk(500)) + if (request.AssignType != AssignTypeEnumType.Tenant) { - await DbContext.InsertAsync(tasks); + (request.Type == DeviceTypeEnumType.Meal).ThrowIfTrue("餐饮设备需分配到厂区级别"); + + if (request.UniqueType == DeviceAssignmentTypeEnumType.Device) + { + if (await DbContext.Queryable() + .Where(x => x.UniqueType == DeviceAssignmentTypeEnumType.Device) + .Where(x => x.AssignType == AssignTypeEnumType.Tenant) + .Where(x => request.Codes.Contains(x.UniqueValue)) + .AnyAsync()) + { + true.ThrowIfTrue("存在设备分配到厂区中"); + } + } + + if (request.UniqueType == DeviceAssignmentTypeEnumType.Group) + { + var result = new List(); + var deviceGroups = await DbContext.Queryable().ToListAsync(); + request.Codes.ForEach(groupCode => result.AddRange(RecursionHelper.HandlerDeviceGroupNextCodes(groupCode, deviceGroups))); + + if (await DbContext.Queryable() + .Where(x => x.UniqueType == DeviceAssignmentTypeEnumType.Group) + .Where(x => x.AssignType == AssignTypeEnumType.Tenant) + .Where(x => result.Contains(x.UniqueValue)) + .AnyAsync()) + { + true.ThrowIfTrue("存在设备组分配到厂区中"); + } + + var deviceCodes = await DbContext.Queryable() + .Where(x => result.Contains(x.GroupCode)) + .Select(x => x.DeviceCode).Distinct() + .ToListAsync(); + + if (await DbContext.Queryable() + .Where(x => x.UniqueType == DeviceAssignmentTypeEnumType.Device) + .Where(x => x.AssignType == AssignTypeEnumType.Tenant) + .Where(x => deviceCodes.Contains(x.UniqueValue)) + .AnyAsync()) + { + true.ThrowIfTrue("设备组存在关联设备已分配到厂区中"); + } + } } } @@ -124,7 +172,19 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService // --------------------------------------------------------------------------------------------------------------------- // - private async Task CheckAssignTopDoorDeviceGroupAsync(DevicePermissionSaveRequest request) + private async Task ChunkInsertAsync(List batch) where T : class, new() + { + foreach (var tasks in batch.Chunk(500)) + { + await DbContext.InsertAsync(tasks); + } + } + + /// + /// 检查是否分配顶级的设备分组 + /// + /// + private static async Task CheckWhetherAssignToTopDeviceGroupAsync(DevicePermissionSaveRequest request) { if (request.UniqueType == DeviceAssignmentTypeEnumType.Group) { @@ -140,18 +200,21 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService } } - + /// + /// 持久化数据 + /// + /// + /// private async Task PersistDataAsync(List dps, DevicePermissionSaveRequest request) { await DbContext.DeleteAsync(dps); //保存配置的权限 if (request.Codes.IsPresent()) { - var currentAssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; var devicePermissions = request.Codes.Select(code => new DevicePermissionEntity { AssignType = request.AssignType, - AssignValue = currentAssignValue, + AssignValue = request.GetActualAssignValue(), UniqueType = request.UniqueType, UniqueValue = code, Type = request.Type, @@ -165,7 +228,6 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService private List GetMyUniqueValues(DeviceAssignmentTypeEnumType uniqueType) { var searchAll = _currentUser.GetRole() is "admin" or "tenant-admin"; - //_myDataPermissionService if (!searchAll && uniqueType == DeviceAssignmentTypeEnumType.Device) { return _myDataPermissionService.GetMyDeviceCodes(); @@ -174,13 +236,17 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService return new List(); } + /// + /// 获取当前分配对应的现有权限 + /// + /// + /// private async Task> GetAssignedDevicePermissionsAsync(DevicePermissionSaveRequest request) { var myData = GetMyUniqueValues(request.UniqueType); - var currentAssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; return await DevicePermission.Where(x => x.AssignType == request.AssignType - && x.AssignValue == currentAssignValue + && x.AssignValue == request.GetActualAssignValue() && x.UniqueType == request.UniqueType && x.Type == request.Type && x.TenantId == CurrentTenantId) @@ -188,6 +254,13 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService .ToListAsync(); } + /// + /// 获取现在权限与当前的分配之间的deviceCode差异 + /// + /// + /// + /// + /// private async Task<(List, List)> GetDiffAsync(DeviceAssignmentTypeEnumType type, List dps, List uniqueValues) { var beforeCodes = dps.Select(x => x.UniqueValue).ToList(); @@ -196,8 +269,8 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService if (type == DeviceAssignmentTypeEnumType.Group) { var deviceGroups = await DbContext.Queryable().ToListAsync(); - beforeCodes = await GetDeviceCodeByGroupAsync(deviceGroups, beforeCodes); - presentCodes = await GetDeviceCodeByGroupAsync(deviceGroups, presentCodes); + beforeCodes = await GetDeviceCodeByGroupAsync(beforeCodes, deviceGroups); + presentCodes = await GetDeviceCodeByGroupAsync(presentCodes, deviceGroups); } var codesToAdd = presentCodes.Except(beforeCodes).ToList(); @@ -207,13 +280,16 @@ public abstract class BasePermissionAnalyzeService : IPermissionAnalyzeService } - private async Task> GetDeviceCodeByGroupAsync(List deviceGroups, List codes) + /// + /// 获取分组下的deviceCode + /// + /// + /// + /// + private async Task> GetDeviceCodeByGroupAsync(List codes, List deviceGroups) { var result = new List(); - foreach (var groupCode in codes) - { - result.AddRange(RecursionHelper.HandlerDeviceGroupNextCodes(groupCode, deviceGroups)); - } + codes.ForEach(groupCode => result.AddRange(RecursionHelper.HandlerDeviceGroupNextCodes(groupCode, deviceGroups))); result = result.Distinct().ToList(); diff --git a/Src/Dlhis.Basic/Device/Services/Implements/DeviceGroupService.cs b/Src/Dlhis.Basic/Device/Services/Implements/DeviceGroupService.cs index a123326e..383fdb60 100644 --- a/Src/Dlhis.Basic/Device/Services/Implements/DeviceGroupService.cs +++ b/Src/Dlhis.Basic/Device/Services/Implements/DeviceGroupService.cs @@ -3,6 +3,8 @@ using Dlhis.Basic.Device.Response; using Dlhis.Entity.Basic.Entity; using Dlhis.Entity.Device.Entities; using Dlhis.Entity.Device.Enums; +using Dlhis.Entity.Sys.Entities; +using Dlhis.Entity.Sys.Enums; using Dlhis.Sys.Api; using Kurisu.AspNetCore.Authentication.Abstractions; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; @@ -14,21 +16,19 @@ namespace Dlhis.Basic.Device.Services.Implements; public class DeviceGroupService : IDeviceGroupService { private readonly IDbContext _dbContext; - private readonly IDevicePermissionAnalyzeService _devicePermissionAnalyzeService; private readonly ICurrentUser _currentUser; + private readonly INamedResolver _namedResolver; private readonly ITenantApi _tenantApi; - private readonly IParallelService _parallelService; public DeviceGroupService(IDbContext dbContext, - IDevicePermissionAnalyzeService devicePermissionAnalyzeService, ICurrentUser currentUser, - ITenantApi tenantApi, IParallelService parallelService) + INamedResolver namedResolver, + ITenantApi tenantApi) { _dbContext = dbContext; - _devicePermissionAnalyzeService = devicePermissionAnalyzeService; _currentUser = currentUser; + _namedResolver = namedResolver; _tenantApi = tenantApi; - _parallelService = parallelService; } @@ -105,24 +105,57 @@ public class DeviceGroupService : IDeviceGroupService await CheckNoNextGroupAsync(group.Code); await CheckGroupTypeMatchAsync(request, group); - _parallelService.Enable = true; - //下发任务 - await _devicePermissionAnalyzeService.GenerateDeviceTasksAsync(async () => + var relationships = await _dbContext.Queryable().Where(x => x.GroupCode == request.GroupCode).ToListAsync(); + await _dbContext.DeleteAsync(relationships); + + var entities = request.DeviceCodes.Select(x => new DeviceGroupRelationshipEntity { - var relationships = await _dbContext.Queryable().Where(x => x.GroupCode == request.GroupCode).ToListAsync(); - await _dbContext.DeleteAsync(relationships); + GroupCode = request.GroupCode, + DeviceCode = x, - var entities = request.DeviceCodes.Select(x => new DeviceGroupRelationshipEntity + TenantId = _currentUser.GetStringTenantId(), + }).ToList(); + + await _dbContext.InsertAsync(entities); + + await PermissionResetAsync(request.GroupCode); + } + + private async Task PermissionResetAsync(Guid groupCode) + { + var deviceGroups = RecursionHelper.HandlerDeviceGroupPreviousCodes(groupCode, await _dbContext.Queryable().ToListAsync()); + + var dps = await _dbContext.Queryable() + .Where(x => x.UniqueType == DeviceAssignmentTypeEnumType.Group) + .Where(x => deviceGroups.Contains(x.UniqueValue)) + .ToListAsync(); + + if (dps.Any()) + { + var type = dps.First().Type; + + foreach (var devicePermissionGroup in dps.GroupBy(x => new { x.AssignType, x.AssignValue, x.TenantId })) { - GroupCode = request.GroupCode, - DeviceCode = x, + var assignType = devicePermissionGroup.Key.AssignType; + var assignValue = devicePermissionGroup.Key.AssignValue; + var tenantId = devicePermissionGroup.Key.TenantId; + var analyzeService = _namedResolver.GetService(PermissionAnalyzeConstants.GetTypeName(assignType)); - TenantId = _currentUser.GetStringTenantId(), - }).ToList(); + var codes = devicePermissionGroup.Select(x => x.UniqueValue).Distinct().ToList(); - await _dbContext.InsertAsync(entities); - }, null); - _parallelService.Enable = false; + await analyzeService.AnalyzeAsync(new DevicePermissionSaveRequest + { + AssignType = assignType, + AssignValue = assignValue, + UniqueType = DeviceAssignmentTypeEnumType.Group, + Codes = codes, + TenantId = tenantId, + Type = type + }); + } + } + + } public async Task> GetDevicesByGroupCodeAsync(Guid code) diff --git a/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionAnalyzeService.cs b/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionAnalyzeService.cs index 03267ad4..d82e09a7 100644 --- a/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionAnalyzeService.cs +++ b/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionAnalyzeService.cs @@ -1,5 +1,4 @@ using System.Collections.Concurrent; -using System.Runtime.CompilerServices; using Dlhis.Basic.DataPermissions; using Dlhis.Basic.Device.Dtos; using Dlhis.Basic.Device.Request; @@ -15,55 +14,34 @@ using Kurisu.AspNetCore.Authentication.Abstractions; using Kurisu.AspNetCore.DataAccess.Entity; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; using Kurisu.AspNetCore.Utils.Extensions; -using SqlSugar; namespace Dlhis.Basic.Device.Services.Implements; public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService { private readonly IDbContext _dbContext; - private readonly IParallelService _parallelService; private readonly ICurrentUser _currentUser; - private readonly ILogger _logger; private readonly IMyDataPermissionService _myDataPermissionService; public DevicePermissionAnalyzeService(IDbContext dbContext, - IParallelService parallelService, ICurrentUser currentUser, - IMyDataPermissionService myDataPermissionService, - ILogger logger) + IMyDataPermissionService myDataPermissionService) { _dbContext = dbContext; - _parallelService = parallelService; _currentUser = currentUser; - _logger = logger; _myDataPermissionService = myDataPermissionService; } public async Task GenerateDeviceTasksAsync(Func func, List userNos) { - var getAllUser = userNos.IsEmpty(); - - //获取所有人的权限 - if (getAllUser) - userNos = await GetPermissionUserNosAsync(); - - var before = await GetAssignDeviceCodesInternalAsync(userNos); + var before = await GetUserAssignDeviceCodesInTenantAsync(userNos); //业务处理 _dbContext.Client.QueryFilter.Restore(); await func(); _dbContext.Client.QueryFilter.ClearAndBackup(); - //获取业务处理后所有人的权限 - if (getAllUser) - { - var nextUserNos = await GetPermissionUserNosAsync(); - if (nextUserNos.Any()) - userNos = userNos.Concat(nextUserNos).Distinct().ToList(); - } - - var current = await GetAssignDeviceCodesInternalAsync(userNos); + var current = await GetUserAssignDeviceCodesInTenantAsync(userNos); var devices = await _dbContext.Queryable().Where(x => x.Enable).ToListAsync(); @@ -72,10 +50,8 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService foreach (var userNo in userNos) { - before.TryGetValue(userNo, out var beforeTenantDeviceCodes); - beforeTenantDeviceCodes ??= new List(); - current.TryGetValue(userNo, out var currentTenantDeviceCodes); - currentTenantDeviceCodes ??= new List(); + var beforeTenantDeviceCodes = before[userNo].ToList(); + var currentTenantDeviceCodes = current[userNo].ToList(); var tenants = new HashSet(); foreach (var item in beforeTenantDeviceCodes) @@ -133,107 +109,14 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService await ChunkInsertAsync(waitAddTasks); await ChunkInsertAsync(waitDeleteTasks); - return new DevicePermissionAssignResponse - { - AddCount = waitAddTasks.Count, - DeleteCount = waitDeleteTasks.Count - }; + return new DevicePermissionAssignResponse(waitAddTasks.Count, waitDeleteTasks.Count); } - public async Task GenerateDeviceTasksV2Async(Func func, List userNos) - { - var before = await GetAssignDeviceCodesInternalAsync(userNos); - //业务处理 - await _dbContext.IgnoreAsync(async () => { await func(); }); - - var current = await GetAssignDeviceCodesInternalAsync(userNos); - - var devices = await _dbContext.Queryable().Where(x => x.Enable).ToListAsync(); - - var waitAddTasks = new List(); - var waitDeleteTasks = new List(); - - foreach (var userNo in userNos) - { - before.TryGetValue(userNo, out var beforeTenantDeviceCodes); - beforeTenantDeviceCodes ??= new List(0); - current.TryGetValue(userNo, out var currentTenantDeviceCodes); - currentTenantDeviceCodes ??= new List(0); - - var tenants = new HashSet(); - foreach (var item in beforeTenantDeviceCodes) - tenants.Add(item.Tenant); - foreach (var item in currentTenantDeviceCodes) - tenants.Add(item.Tenant); - - foreach (var tenant in tenants) - { - var currentCodes = currentTenantDeviceCodes.FirstOrDefault(x => x.Tenant == tenant)?.Codes?.ToList() ?? new List(); - var beforeCodes = beforeTenantDeviceCodes.FirstOrDefault(x => x.Tenant == tenant)?.Codes?.ToList() ?? new List(); - - var addItems = currentCodes.Except(beforeCodes).ToList(); - var deletedItems = beforeCodes.Except(currentCodes).ToList(); - - if (!deletedItems.Any() && !addItems.Any()) - { - continue; - } - - //下发任务创建 - deletedItems.ForEach(x => waitDeleteTasks.Add(new DeviceTaskEntity - { - DeviceUniqueNo = devices.First(item => item.Code == x).UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Type = DeviceTaskEnumType.Delete, - CancellationId = 0, - DeviceType = devices.First(item => item.Code == x).Type, - UserNo = userNo, - Version = 0, - TenantId = tenant, - Source = DeviceTaskSourceEnumType.Manually - })); - - addItems.ForEach(x => waitAddTasks.Add(new DeviceTaskEntity - { - DeviceUniqueNo = devices.First(item => item.Code == x).UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Type = DeviceTaskEnumType.Add, - DeviceType = devices.First(item => item.Code == x).Type, - UserNo = userNo, - Version = 0, - TenantId = tenant, - Source = DeviceTaskSourceEnumType.Manually - })); - } - } - - await ChunkInsertAsync(waitAddTasks); - await ChunkInsertAsync(waitDeleteTasks); - - return new DevicePermissionAssignResponse - { - AddCount = waitAddTasks.Count, - DeleteCount = waitDeleteTasks.Count - }; - } - - private async Task ChunkInsertAsync(List batch) where T : class, new() - { - foreach (var tasks in batch.Chunk(500)) - { - await _dbContext.InsertAsync(tasks.ToList()); - } - } - - - public async Task>> GetAssignDeviceCodesInternalAsync(List userNos, params AssignTypeEnumType[] ignoreAssignTypes) + public async Task>> GetUserAssignDeviceCodesWithTypeInTenantAsync(List userNos, params AssignTypeEnumType[] ignoreAssignTypes) { var gainfos = await _dbContext.Queryable().Where(x => userNos.Contains(x.No)).ToListAsync(); - if (!gainfos.Any()) - { - return new Dictionary>(); - } + if (!gainfos.Any()) return new Dictionary>(); var devices = await _dbContext.Queryable().Where(x => x.Enable).ToListAsync(); @@ -247,318 +130,75 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService var deviceRelationships = await _dbContext.Queryable().ToListAsync(); var departments = await _dbContext.Queryable().ToListAsync(); - var result = new ConcurrentDictionary>(); - //var total = gainfos.Count; + var result = new ConcurrentDictionary>(); gainfos.ParallelForEach(gainfo => { - var gainfoDto = new GainfoDto + var internalIgnoreAssignTypes = new List(); + internalIgnoreAssignTypes.AddRange(ignoreAssignTypes); + if (gainfo.Type == GainfoUserTypeEnumType.Outsource && (enableFactoryPermissions.FirstOrDefault(x => x.TenantId == gainfo.Factory)?.EnableOutsourceDown ?? true) == false) { - Id = gainfo.Id, - No = gainfo.No, - Code = gainfo.Code, - Name = gainfo.Name, - Workplace = gainfo.Workplace, - Factory = gainfo.Factory, - DepartmentNo = gainfo.DepartmentNo, - IsOutsource = gainfo.Type == GainfoUserTypeEnumType.Outsource, - EnableFactoryPermission = enableFactoryPermissions.FirstOrDefault(x => x.TenantId == gainfo.Factory)?.EnableOutsourceDown ?? true + internalIgnoreAssignTypes.Add(AssignTypeEnumType.Tenant); + } + + var analyzePack = new AnalyzePackDto + { + UserNo = gainfo.No, + UserDepartment = gainfo.Factory + ":" + gainfo.DepartmentNo, + UserFactory = gainfo.Factory, + UserGainfoGroupCodes = gainfoGroupRelationships.Where(x => x.UserNo == gainfo.No).Select(x => x.GroupCode), + DeviceCodes = devices.WhereIf(gainfo.Type == GainfoUserTypeEnumType.Outsource, x => x.Type != DeviceTypeEnumType.Meal).Select(x => x.Code), //外包人员不允许餐饮 + IgnoreAssignTypeTypes = internalIgnoreAssignTypes }; - var codes = GetAssignDeviceCodesInternal2(gainfoDto, gainfoGroups, gainfoGroupRelationships, devicePermissions, deviceGroups, deviceRelationships, devices, departments, ignoreAssignTypes); - result.TryAdd(gainfo.No, codes); + var codes = GetAssignDeviceCodesInternal(analyzePack, + gainfoGroups, + devicePermissions, + deviceGroups, + deviceRelationships, + departments); - // Interlocked.Decrement(ref total); - // _logger.LogInformation("剩余:{count}", total); + result.TryAdd(gainfo.No, codes); }); return result.ToDictionary(x => x.Key, x => x.Value); } - public async Task>> GetAssignDeviceCodesInternalAsync(List userNos) - { - var devices = await _dbContext.Queryable().Where(x => x.Enable).ToListAsync(); - var deviceUniqueNos = devices.Select(x => x.UniqueNo).ToList(); - var registries = await _dbContext.Queryable() - .Where(x => deviceUniqueNos.Contains(x.DeviceUniqueNo)) - .Where(x => !SqlFunc.IsNullOrEmpty(x.BusinessPlaceCode)) - .ToListAsync(); - - var gainfos = await _dbContext.Queryable().Where(x => userNos.Contains(x.No)).ToListAsync(); - if (!gainfos.Any()) - { - return new Dictionary>(); - } - - var enableFactoryPermissions = await _dbContext.Queryable().ToListAsync(); - - var gainfoGroupRelationships = await _dbContext.Queryable().Where(x => userNos.Contains(x.UserNo)).ToListAsync(); - var devicePermissions = await _dbContext.Queryable().ToListAsync(); - var deviceGroups = await _dbContext.Queryable().ToListAsync(); - var deviceRelationships = await _dbContext.Queryable().ToListAsync(); - var departments = await _dbContext.Queryable().ToListAsync(); - - if (_parallelService.Enable) - { - var result = new ConcurrentDictionary>(); - var total = gainfos.Count; - Parallel.ForEach(gainfos, new ParallelOptions { MaxDegreeOfParallelism = 4 }, gainfo => - { - var gainfoDto = new GainfoDto - { - Id = gainfo.Id, - No = gainfo.No, - Code = gainfo.Code, - Name = gainfo.Name, - Workplace = gainfo.Workplace, - Factory = gainfo.Factory, - DepartmentNo = gainfo.DepartmentNo, - IsOutsource = gainfo.Type == GainfoUserTypeEnumType.Outsource, - EnableFactoryPermission = enableFactoryPermissions.FirstOrDefault(x => x.TenantId == gainfo.Factory)?.EnableOutsourceDown ?? true - }; - - var codes = GetAssignDeviceCodesInternal(gainfoDto, gainfoGroupRelationships, devicePermissions, deviceGroups, deviceRelationships, registries, devices, departments); - result.TryAdd(gainfo.No, codes); - - Interlocked.Decrement(ref total); - _logger.LogInformation("剩余:{count}", total); - }); - - return result.ToDictionary(x => x.Key, x => x.Value); - } - else - { - var result = new Dictionary>(); - var total = gainfos.Count; - foreach (var gainfo in gainfos) - { - var gainfoDto = new GainfoDto - { - Id = gainfo.Id, - No = gainfo.No, - Code = gainfo.Code, - Name = gainfo.Name, - Workplace = gainfo.Workplace, - Factory = gainfo.Factory, - DepartmentNo = gainfo.DepartmentNo, - IsOutsource = gainfo.Type == GainfoUserTypeEnumType.Outsource, - EnableFactoryPermission = enableFactoryPermissions.FirstOrDefault(x => x.TenantId == gainfo.Factory)?.EnableOutsourceDown ?? true - }; - - var codes = GetAssignDeviceCodesInternal(gainfoDto, gainfoGroupRelationships, devicePermissions, deviceGroups, deviceRelationships, registries, devices, departments); - result.Add(gainfo.No, codes); - total--; - _logger.LogInformation("剩余:{count}", total); - } - - return result; - } - } - - public async Task> GetAssignmentsAsync(DeviceGetAssignmentsRequest request) - { - request.AssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; - var role = _currentUser.GetRole(); - var isAll = role is "admin" or "tenant-admin"; - var deviceCodes = _myDataPermissionService.GetMyDeviceCodes(); - - return await _dbContext.Queryable() - .Where(x => x.AssignType == request.AssignType) - .Where(x => x.AssignValue == request.AssignValue) - .Where(x => x.UniqueType == request.UniqueType) - .WhereIF(request.UniqueType == DeviceAssignmentTypeEnumType.Device && !isAll, x => deviceCodes.Contains(x.UniqueValue)) - .Where(x => x.Type == request.Type) - .Select(x => x.UniqueValue) - .ToListAsync(); - } - - public async Task> GetAssignmentUniqueAsync(DeviceGetAssignmentUniquesRequest request) - { - var nos = await _dbContext.Queryable() - .Where(x => x.UniqueType == request.UniqueType) - .Where(x => x.UniqueValue == request.UniqueValue) - .Where(x => x.AssignType == AssignTypeEnumType.User) - .Where(x => x.Type == request.Type) - .Select(x => x.AssignValue) - .ToListAsync(); - - return await _dbContext.Queryable().Where(x => nos.Contains(x.No)).Select(x => new GainfoDto - { - Id = x.Id, - Code = x.Code, - Name = x.Name, - Workplace = x.Workplace, - Factory = x.Factory - }).ToListAsync(); - } - - public async Task> GetAssignDeviceCodesAsync(string userCode) - { - var userNo = await _dbContext.Queryable().Where(x => x.Code == userCode || x.No == userCode).Select(x => x.No).SingleAsync(); - var result = await GetAssignDeviceCodesInternalAsync(new List { userNo }); - return result.First().Value.SelectMany(x => x.Codes).ToList(); - } - - private static List GetAssignDeviceCodesInternal( - GainfoDto gainfo, - List gainfoGroupRelationships, - List devicePermissions, - List deviceGroups, - List deviceGroupRelationships, - List deviceRegistries, - List devices, List departments) - { - if (gainfo.IsOutsource) - { - //外包人员不允许餐饮 - devices = devices.Where(x => x.Type != DeviceTypeEnumType.Meal).ToList(); - } - - var userNo = gainfo.No; - - var deviceDtos = new List(); - var deviceGroupDtos = new List(); - var businessPlaceDtos = new List(); - - //获取人员的分组,跨基地 - var gainfoGroups = gainfoGroupRelationships.Where(x => x.UserNo == userNo).Select(x => x.GroupCode).ToList(); - - //按用户 - var du = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.User, userNo); - var gu = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.User, userNo); - var pu = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.BusinessPlace, AssignTypeEnumType.User, userNo); - deviceDtos.AddRange(du); - deviceGroupDtos.AddRange(gu); - businessPlaceDtos.AddRange(pu); - - //按用户组 - foreach (var groupCode in gainfoGroups) - { - var dg = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Group, groupCode.ToString()); - var gg = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Group, groupCode.ToString()); - var pg = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.BusinessPlace, AssignTypeEnumType.Group, groupCode.ToString()); - deviceDtos.AddRange(dg); - deviceGroupDtos.AddRange(gg); - businessPlaceDtos.AddRange(pg); - } - - //按部门 - var currentAssignValue = gainfo.Factory + ":" + gainfo.DepartmentNo; - var dd = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Department, currentAssignValue); - var gd = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Department, currentAssignValue); - var pd = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.BusinessPlace, AssignTypeEnumType.Department, currentAssignValue); - deviceDtos.AddRange(dd); - deviceGroupDtos.AddRange(gd); - businessPlaceDtos.AddRange(pd); - - //按厂区 - if (!gainfo.IsOutsource || gainfo.EnableFactoryPermission) - { - var dt = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Tenant, gainfo.Factory); - var gt = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Tenant, gainfo.Factory); - var pt = GetAssignCodesInternal(devicePermissions, deviceGroups, departments, DeviceAssignmentTypeEnumType.BusinessPlace, AssignTypeEnumType.Tenant, gainfo.Factory); - deviceDtos.AddRange(dt); - deviceGroupDtos.AddRange(gt); - businessPlaceDtos.AddRange(pt); - } - - var deviceGroupCodes = deviceGroupDtos.SelectMany(x => x.Codes).Distinct().ToList(); - var businessPlaceCodes = businessPlaceDtos.SelectMany(x => x.Codes).Distinct().ToList(); - - var deviceCodesByGroup = deviceGroupRelationships.Where(x => deviceGroupCodes.Contains(x.GroupCode)) - .GroupBy(x => x.TenantId) - .Select(x => new UserTenantDeviceCodeDto - { - Tenant = x.Key, - Codes = x.Select(item => item.DeviceCode).Distinct().ToList() - }); - - var placeGroup = deviceRegistries.Where(x => businessPlaceCodes.Contains(x.BusinessPlaceCode!.Value)) - .GroupBy(x => x.TenantId) - .Select(x => - { - var currentDeviceUniqueNos = x.Select(item => item.DeviceUniqueNo).ToList(); - - return new UserTenantDeviceCodeDto - { - Tenant = x.Key, - Codes = devices.Where(d => currentDeviceUniqueNos.Contains(d.UniqueNo)).Select(d => d.Code).Distinct().ToList() - }; - }).ToList(); - - deviceDtos.AddRange(deviceCodesByGroup); - deviceDtos.AddRange(placeGroup); - - return deviceDtos.GroupBy(x => x.Tenant).Select(x => - { - var dto = new UserTenantDeviceCodeDto - { - Tenant = x.Key, - Codes = x.SelectMany(item => item.Codes).Distinct().ToList() - }; - - dto.Codes = dto.Codes.Where(p => devices.Any(item => item.Code == p)).ToList(); - - return dto; - }).ToList(); - } - - public static List GetAssignDeviceCodesInternal2( - GainfoDto gainfo, + private static IEnumerable GetAssignDeviceCodesInternal( + AnalyzePackDto analyzePack, List gainfoGroups, - List gainfoGroupRelationships, List devicePermissions, List deviceGroups, List deviceGroupRelationships, - List devices, List departments, params AssignTypeEnumType[] ignoreAssignTypes) + List departments) { - if (gainfo.IsOutsource) - { - //外包人员不允许餐饮 - devices = devices.Where(x => x.Type != DeviceTypeEnumType.Meal).ToList(); - } - - var deviceCodes = devices.Select(x => x.Code).ToList(); - var deviceDtos = new List(); var deviceGroupDtos = new List(); - //获取人员的分组,跨基地 - var myGainfoGroups = gainfoGroupRelationships.Where(x => x.UserNo == gainfo.No).Select(x => x.GroupCode).ToList(); - - if (ignoreAssignTypes.IsEmpty() || !ignoreAssignTypes.Contains(AssignTypeEnumType.User)) + foreach (var assignType in new[] { AssignTypeEnumType.User, AssignTypeEnumType.Group, AssignTypeEnumType.Department, AssignTypeEnumType.Tenant }) { - //按用户 - deviceDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.User, gainfo.No)); - deviceGroupDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.User, gainfo.No)); - } - - if (ignoreAssignTypes.IsEmpty() || !ignoreAssignTypes.Contains(AssignTypeEnumType.Group)) - { - //按用户组 - foreach (var groupCode in myGainfoGroups) + var assignValues = assignType switch { - deviceDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Group, groupCode.ToString())); - deviceGroupDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Group, groupCode.ToString())); + AssignTypeEnumType.User => new[] { analyzePack.UserNo }, + AssignTypeEnumType.Group => analyzePack.UserGainfoGroupCodes.Select(x => x.ToString()).ToArray(), + AssignTypeEnumType.Department => new[] { analyzePack.UserDepartment }, + AssignTypeEnumType.Tenant => new[] { analyzePack.UserFactory }, + AssignTypeEnumType.Role => throw new ArgumentOutOfRangeException(), + _ => throw new ArgumentOutOfRangeException() + }; + + if (analyzePack.IgnoreAssignTypeTypes.Contains(assignType)) + { + continue; } - } - if (ignoreAssignTypes.IsEmpty() || !ignoreAssignTypes.Contains(AssignTypeEnumType.Department)) - { - //按部门 - var currentAssignValue = gainfo.Factory + ":" + gainfo.DepartmentNo; - deviceDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Department, currentAssignValue)); - deviceGroupDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Department, currentAssignValue)); - } - - if (ignoreAssignTypes.IsEmpty() || !ignoreAssignTypes.Contains(AssignTypeEnumType.Tenant)) - { - //按厂区 - if (!gainfo.IsOutsource || gainfo.EnableFactoryPermission) + foreach (var assignValue in assignValues) { - deviceDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Device, AssignTypeEnumType.Tenant, gainfo.Factory)); - deviceGroupDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, DeviceAssignmentTypeEnumType.Group, AssignTypeEnumType.Tenant, gainfo.Factory)); + deviceDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, + DeviceAssignmentTypeEnumType.Device, assignType, assignValue)); + deviceGroupDtos.AddRange(GetMyTypeDevicePermissionAsync(devicePermissions, gainfoGroups, deviceGroups, departments, + DeviceAssignmentTypeEnumType.Group, assignType, assignValue)); } } @@ -567,17 +207,17 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService { var tenant = x.Tenant; - var deviceGroupCodes = x.Codes.SelectMany(item => item.Codes); - var type = x.Codes.ElementAt(0).AssignType; + var deviceGroupCodes = x.AssignTypes.SelectMany(item => item.Codes); + var type = x.AssignTypes.ElementAt(0).AssignType; return new TenantAssignTypeDeviceCode { Tenant = tenant, - Codes = new List + AssignTypes = new[] { - new() + new AssignTypeDeviceCode { AssignType = type, - Codes = deviceGroupRelationships.Where(item => deviceGroupCodes.Contains(item.GroupCode)).Select(item => item.DeviceCode).ToList() + Codes = deviceGroupRelationships.Where(item => deviceGroupCodes.Contains(item.GroupCode)).Select(item => item.DeviceCode) } } }; @@ -588,69 +228,17 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService var dto = new TenantAssignTypeDeviceCode { Tenant = x.Key, - Codes = x.SelectMany(p => p.Codes) + AssignTypes = x.SelectMany(p => p.AssignTypes) .GroupBy(p => p.AssignType) .Select(p => new AssignTypeDeviceCode { AssignType = p.Key, - Codes = p.SelectMany(item => deviceCodes.Where(it => item.Codes.Contains(it))) + Codes = p.SelectMany(item => analyzePack.DeviceCodes.Where(it => item.Codes.Contains(it))) }) }; return dto; - }).ToList(); - } - - private static List GetAssignCodesInternal( - List devicePermissions, List deviceGroups, List departments, - DeviceAssignmentTypeEnumType uniqueType, AssignTypeEnumType assignType, string assignValue) - { - var tenantDevicePermissions = devicePermissions - .Where(x => x.UniqueType == uniqueType - && x.AssignType == assignType - && x.AssignValue == assignValue) - .GroupBy(x => x.TenantId) - .Select(x => new UserTenantDeviceCodeDto { Tenant = x.Key, Codes = x.Select(p => p.UniqueValue) }) - .ToList(); - - //处理获取设备分组的情况 - if (uniqueType == DeviceAssignmentTypeEnumType.Group) - { - //开始递归处理 - var tops = deviceGroups.Where(x => !x.PCode.HasValue).ToList(); - tops.ForEach(x => { DeviceGroupRecursionGetNext(x, deviceGroups, tenantDevicePermissions, tenantDevicePermissions.SelectMany(item => item.Codes).Contains(x.Code)); }); - } - - if (assignType == AssignTypeEnumType.Department) - { - //递归向上获取 assignValue = department.No - var arr = assignValue.Split(":"); - var tenantId = arr.First(); - var currentDepartmentNo = arr.Last(); - var departmentNos = new List(12) { currentDepartmentNo }; - DepartmentRecursionGetPNo(currentDepartmentNo, departments, departmentNos); - - departmentNos = departmentNos.Select(x => tenantId + ":" + x).ToList(); - - tenantDevicePermissions = devicePermissions - .Where(x => x.UniqueType == uniqueType) - .Where(x => x.AssignType == assignType) - .Where(x => departmentNos.Contains(x.AssignValue)) - .GroupBy(x => x.TenantId) - .Select(x => new UserTenantDeviceCodeDto { Tenant = x.Key, Codes = x.Select(p => p.UniqueValue) }) - .ToList(); - } - - return tenantDevicePermissions.GroupBy(x => x.Tenant).Select(x => - { - var tenant = x.Key; - - return new UserTenantDeviceCodeDto - { - Tenant = tenant, - Codes = x.SelectMany(item => item.Codes).ToList() - }; - }).ToList(); + }); } private static List GetCurrentAssignTypePermissions( @@ -661,7 +249,6 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService AssignTypeEnumType assignType, string assignValue) { - //处理分配到部门 if (assignType == AssignTypeEnumType.Department) { // 2401:00001 @@ -695,15 +282,16 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService //user / tenant return devicePermissions - .Where(x => x.UniqueType == uniqueType //设备/设备组 - && x.AssignType == assignType // user/group/department/tenant + .Where(x => x.UniqueType == uniqueType + && x.AssignType == assignType && x.AssignValue == assignValue) .GroupBy(x => x.TenantId) .Select(x => new UserTenantDeviceCodeDto { Tenant = x.Key, Codes = x.Select(p => p.UniqueValue) }) .ToList(); } - private static List GetMyTypeDevicePermissionAsync( + + private static IEnumerable GetMyTypeDevicePermissionAsync( List devicePermissions, List gainfoGroups, List deviceGroups, @@ -736,120 +324,83 @@ public class DevicePermissionAnalyzeService : IDevicePermissionAnalyzeService return new TenantAssignTypeDeviceCode { Tenant = tenant, - Codes = new List + AssignTypes = new[] { - new() + new AssignTypeDeviceCode { AssignType = assignType, - Codes = x.SelectMany(item => item.Codes), + Codes = x.SelectMany(item => item.Codes) } } }; - }).ToList(); + }); } - /// - /// 获取当前基地有权限的用户 - /// - /// - private async Task> GetPermissionUserNosAsync() + private async Task ChunkInsertAsync(List batch) where T : class, new() { - var permissions = await _dbContext.Queryable().ToListAsync(); + foreach (var tasks in batch.Chunk(500)) + { + await _dbContext.InsertAsync(tasks.ToList()); + } + } - //User - var userNos = permissions.Where(x => x.AssignType == AssignTypeEnumType.User) + + public async Task>> GetUserAssignDeviceCodesInTenantAsync(List userNos, params AssignTypeEnumType[] ignoreAssignTypes) + { + var result = await GetUserAssignDeviceCodesWithTypeInTenantAsync(userNos, ignoreAssignTypes); + + return result.ToDictionary(x => x.Key, x => x.Value.GroupBy(p => p.Tenant).Select(item => + { + return new UserTenantDeviceCodeDto + { + Tenant = item.Key, + Codes = item.SelectMany(p => p.AssignTypes).SelectMany(p => p.Codes).Distinct().ToList(), + }; + })); + } + + + public async Task> GetAssignmentsAsync(DeviceGetAssignmentsRequest request) + { + var currentAssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; + + var deviceCodes = _currentUser.GetRole() is "admin" or "tenant-admin" ? new List() : _myDataPermissionService.GetMyDeviceCodes(); + + return await _dbContext.Queryable() + .Where(x => x.AssignType == request.AssignType) + .Where(x => x.AssignValue == currentAssignValue) + .Where(x => x.UniqueType == request.UniqueType) + .WhereIF(deviceCodes.Any() && request.UniqueType == DeviceAssignmentTypeEnumType.Device, x => deviceCodes.Contains(x.UniqueValue)) + .Where(x => x.Type == request.Type) + .Select(x => x.UniqueValue) + .ToListAsync(); + } + + public async Task> GetAssignmentUniqueAsync(DeviceGetAssignmentUniquesRequest request) + { + var nos = await _dbContext.Queryable() + .Where(x => x.UniqueType == request.UniqueType) + .Where(x => x.UniqueValue == request.UniqueValue) + .Where(x => x.AssignType == AssignTypeEnumType.User) + .Where(x => x.Type == request.Type) .Select(x => x.AssignValue) - .Distinct() - .ToList(); - - //Group - var groupCodes = permissions.Where(x => x.AssignType == AssignTypeEnumType.Group) - .Select(x => Guid.Parse(x.AssignValue)) - .Distinct() - .ToList(); - var userNosByGroup = await _dbContext.Queryable() - .Where(x => groupCodes.Contains(x.GroupCode)) - .Select(x => x.UserNo) .ToListAsync(); - //Department - var tenantDepartmentNos = permissions.Where(x => x.AssignType == AssignTypeEnumType.Department) - .Where(x => x.AssignValue.Contains(':')) - .Select(x => - { - var arr = x.AssignValue.Split(':'); - return new - { - Factory = arr[0], DepartmentNo = arr[1] - }; - }) - .GroupBy(x => x.Factory) - .ToDictionary(x => x.Key, x => x.Select(p => p.DepartmentNo).Distinct().ToList()); - var departments = await _dbContext.Queryable().ToListAsync(); - - var gainfoByDeptWhere = LinqExpressionExtensions.False(); - foreach ((string factory, List departmentNos) in tenantDepartmentNos) + return await _dbContext.Queryable().Where(x => nos.Contains(x.No)).Select(x => new GainfoDto { - var departmentNosToSearch = new List(); - foreach (var d in departmentNos) - { - departmentNosToSearch.Add(d); - RecursionGetNextAllDepartment(d, departments, departmentNosToSearch); - } - - gainfoByDeptWhere = gainfoByDeptWhere.Or(x => x.Factory == factory && departmentNosToSearch.Contains(x.DepartmentNo)); - } - - var userNosByDepartment = await _dbContext.Queryable() - .Where(gainfoByDeptWhere) - .Select(x => x.No) - .ToListAsync(); - - - //Tenant - var tenants = permissions.Where(x => x.AssignType == AssignTypeEnumType.Tenant).Select(x => x.AssignValue).Distinct().ToList(); - var userNosByWerk = await _dbContext.Queryable().Where(x => tenants.Contains(x.Factory)).Select(x => x.No).ToListAsync(); - - return userNos.Concat(userNosByGroup).Concat(userNosByDepartment).Concat(userNosByWerk).Distinct().ToList(); - - void RecursionGetNextAllDepartment(string current, List data, List result) - { - var next = data.Where(x => x.PNo == current); - foreach (var item in next.Select(x => x.No)) - { - result.Add(item); - RecursionGetNextAllDepartment(item, data, result); - } - } + Id = x.Id, + Code = x.Code, + Name = x.Name, + Workplace = x.Workplace, + Factory = x.Factory + }).ToListAsync(); } - - [MethodImpl(MethodImplOptions.AggressiveInlining)] - static void DepartmentRecursionGetPNo(string current, List data, List result) + public async Task> GetAssignDeviceCodesAsync(string userCode) { - var p = data.FirstOrDefault(x => x.No == current)?.PNo; - if (!p.IsPresent()) - { - return; - } - - result.Add(p); - DepartmentRecursionGetPNo(p, data, result); - } - - [MethodImpl(MethodImplOptions.AggressiveInlining)] - static void DeviceGroupRecursionGetNext(DeviceGroupEntity current, List currentDeviceGroups, List result, bool add) - { - var next = currentDeviceGroups.Where(x => x.PCode == current.Code).ToList(); - foreach (var item in next) - { - if (add) - { - result.Add(new UserTenantDeviceCodeDto { Tenant = item.TenantId, Codes = new List { item.Code } }); - } - - DeviceGroupRecursionGetNext(item, currentDeviceGroups, result, result.SelectMany(x => x.Codes).Contains(item.Code)); - } + var userNo = await _dbContext.Queryable().Where(x => x.Code == userCode || x.No == userCode).Select(x => x.No).SingleAsync(); + var result = await GetUserAssignDeviceCodesInTenantAsync(new List { userNo }); + return result.First().Value.SelectMany(x => x.Codes).ToList(); } } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionService.cs b/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionService.cs index c0a38b64..fa057727 100644 --- a/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionService.cs +++ b/Src/Dlhis.Basic/Device/Services/Implements/DevicePermissionService.cs @@ -1,5 +1,4 @@ -using Dlhis.Basic.DataPermissions; -using Dlhis.Basic.Device.Dtos; +using Dlhis.Basic.Device.Dtos; using Dlhis.Basic.Device.Request; using Dlhis.Basic.Device.Response; using Dlhis.Entity.Basic.Entity; @@ -11,10 +10,8 @@ using Dlhis.Entity.Visitor.Entity; using Dlhis.Sys.Api; using Kurisu.AspNetCore.Authentication.Abstractions; using Kurisu.AspNetCore.DataAccess.Dto; -using Kurisu.AspNetCore.DataAccess.Entity; using Kurisu.AspNetCore.DataAccess.SqlSugar.Extensions; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; -using Kurisu.AspNetCore.Scope; using Kurisu.AspNetCore.Utils.Extensions; using OfficeOpenXml; using SqlSugar; @@ -24,25 +21,19 @@ namespace Dlhis.Basic.Device.Services.Implements; public class DevicePermissionService : IDevicePermissionService { private readonly IDbContext _dbContext; - private readonly IMyDataPermissionService _myDataPermissionService; private readonly ITenantApi _tenantApi; - private readonly IParallelService _parallelService; private readonly INamedResolver _namedResolver; private readonly IDevicePermissionAnalyzeService _devicePermissionAnalyzeService; private readonly ICurrentUser _currentUser; public DevicePermissionService(IDbContext dbContext, - IMyDataPermissionService myDataPermissionService, ITenantApi tenantApi, - IParallelService parallelService, INamedResolver namedResolver, IDevicePermissionAnalyzeService devicePermissionAnalyzeService, ICurrentUser currentUser) { _dbContext = dbContext; - _myDataPermissionService = myDataPermissionService; _tenantApi = tenantApi; - _parallelService = parallelService; _namedResolver = namedResolver; _devicePermissionAnalyzeService = devicePermissionAnalyzeService; _currentUser = currentUser; @@ -50,252 +41,9 @@ public class DevicePermissionService : IDevicePermissionService public async Task AssignAsync(DevicePermissionSaveRequest request) { - await _namedResolver.GetService(PermissionAnalyzeConstants.GetTypeName(request.AssignType)).AnalyzeAsync(request); - - return null; - await CheckAssignTopDoorDeviceGroupAsync(request); - - var currentTenantId = _currentUser.GetStringTenantId(); - var role = _currentUser.GetRole(); - var isAll = role is "admin" or "tenant-admin"; - var deviceCodes = isAll ? new List() : _myDataPermissionService.GetMyDeviceCodes(); - - _parallelService.Enable = true; - return await _devicePermissionAnalyzeService.GenerateDeviceTasksAsync(async () => - { - request.AssignValue = request.AssignType == AssignTypeEnumType.Department ? request.TenantId + ":" + request.AssignValue : request.AssignValue; - - await _dbContext.IgnoreAsync(async () => - { - //删除当前匹配的基地权限 - var p = await _dbContext.Queryable() - .Where(x => x.AssignType == request.AssignType) - .Where(x => x.AssignValue == request.AssignValue) - .Where(x => x.UniqueType == request.UniqueType) - .WhereIF(request.UniqueType == DeviceAssignmentTypeEnumType.Device && !isAll, x => deviceCodes.Contains(x.UniqueValue)) - .Where(x => x.Type == request.Type) - .Where(x => x.TenantId == currentTenantId) - .ToListAsync(); - - await _dbContext.DeleteAsync(p); - - //保存配置的权限 - if (request.Codes.IsPresent()) - { - var devicePermissions = request.Codes.Select(code => new DevicePermissionEntity - { - AssignType = request.AssignType, - AssignValue = request.AssignValue, - UniqueType = request.UniqueType, - UniqueValue = code, - Type = request.Type, - TenantId = currentTenantId - }).ToList(); - - await _dbContext.InsertAsync(devicePermissions); - } - }); - }, null); - } - - - private async Task CheckAssignTopDoorDeviceGroupAsync(DevicePermissionSaveRequest request) - { - if (request.UniqueType == DeviceAssignmentTypeEnumType.Group) - { - await Scoped.Temp.Value.CreateAsync(async sp => - { - var currentDb = sp.GetService(); - await currentDb.IgnoreAsync(async () => - { - var dgs = await currentDb.Queryable().Where(x => request.Codes.Contains(x.Code)).ToListAsync(); - dgs.Any(x => x.TenantId.IsEmpty()).ThrowIfTrue("不可分配顶级分组节点"); - }); - }); - } - } - - - public async Task GenerateTasksAsync(List addDeviceCodes, List deleteDeviceCodes, List gainfoNos) - { - var allDeviceCodes = addDeviceCodes.Concat(deleteDeviceCodes).ToList(); - var devices = await _dbContext.Queryable() - .Where(x => allDeviceCodes.Contains(x.Code)) - .Select(x => new { x.Code, x.UniqueNo, x.Type, x.TenantId }) - .ToListAsync(); - - var tasks = new List(); - foreach (var gainfoNo in gainfoNos) - { - tasks.AddRange(addDeviceCodes.Select(x => - { - var d = devices.First(item => item.Code == x); - return new DeviceTaskEntity - { - Type = DeviceTaskEnumType.Add, - DeviceType = d.Type, - UserId = null, - UserNo = gainfoNo, - DeviceUniqueNo = d.UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Version = 0, - ResultMessage = null, - CancellationId = 0, - Source = DeviceTaskSourceEnumType.Manually, - Priority = 0, - TenantId = d.TenantId, - }; - }).ToList()); - - tasks.AddRange(deleteDeviceCodes.Select(x => - { - var d = devices.First(item => item.Code == x); - return new DeviceTaskEntity - { - Type = DeviceTaskEnumType.Delete, - DeviceType = d.Type, - UserId = null, - UserNo = gainfoNo, - DeviceUniqueNo = d.UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Version = 0, - ResultMessage = null, - CancellationId = 0, - Source = DeviceTaskSourceEnumType.Manually, - Priority = 0, - TenantId = d.TenantId, - }; - }).ToList()); - } - - foreach (var items in tasks.Where(x => x.Type == DeviceTaskEnumType.Add).Chunk(500)) - { - await _dbContext.InsertAsync(items.ToList()); - } - - return new DevicePermissionAssignResponse - { - AddCount = addDeviceCodes.Count * gainfoNos.Count, - DeleteCount = deleteDeviceCodes.Count * gainfoNos.Count - }; - } - - - public async Task AssignDeviceGroupToTenantAsync(string currentTenantId, DevicePermissionSaveRequest request) - { - var groupData = await _dbContext.Queryable() - .Where(x => x.AssignType == AssignTypeEnumType.Tenant) - .Where(x => x.AssignValue == request.AssignValue) - .Where(x => x.UniqueType == request.UniqueType) - .Where(x => x.Type == request.Type) - .Where(x => x.TenantId == currentTenantId) - .ToListAsync(); - - var gainfoNos = await _dbContext.Queryable().Where(x => x.Factory == request.AssignValue).Select(x => x.No).ToListAsync(); - - var beforeDeviceCodes = groupData.Select(x => x.UniqueValue).ToList(); - var presentDeviceCodes = request.Codes.IsPresent() ? request.Codes : new List(); - - var addDeviceGroupCodes = presentDeviceCodes.Except(beforeDeviceCodes).ToList(); - var deleteDeviceGroupCodes = beforeDeviceCodes.Except(presentDeviceCodes).ToList(); - - await _dbContext.DeleteAsync(groupData); - //保存配置的权限 - if (request.Codes.IsPresent()) - { - var devicePermissions = request.Codes.Select(code => new DevicePermissionEntity - { - AssignType = request.AssignType, - AssignValue = request.AssignValue, - UniqueType = request.UniqueType, - UniqueValue = code, - Type = request.Type, - TenantId = currentTenantId - }).ToList(); - - await _dbContext.InsertAsync(devicePermissions); - } - - var deviceGroups = await _dbContext.Queryable().ToListAsync(); - - var addDevices = await GetDevicesByGroupsAsync(deviceGroups, deviceGroups.Where(x => addDeviceGroupCodes.Contains(x.Code)).ToList()); - var deleteDevices = await GetDevicesByGroupsAsync(deviceGroups, deviceGroups.Where(x => deleteDeviceGroupCodes.Contains(x.Code)).ToList()); - - var tasks = new List(); - foreach (var gainfoNo in gainfoNos) - { - tasks.AddRange(addDevices.Select(x => new DeviceTaskEntity - { - Type = DeviceTaskEnumType.Add, - DeviceType = x.Type, - UserId = null, - UserNo = gainfoNo, - DeviceUniqueNo = x.UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Version = 0, - ResultMessage = null, - CancellationId = 0, - Source = DeviceTaskSourceEnumType.Manually, - Priority = 0, - TenantId = x.TenantId, - }).ToList()); - - tasks.AddRange(deleteDevices.Select(x => new DeviceTaskEntity - { - Type = DeviceTaskEnumType.Delete, - DeviceType = x.Type, - UserId = null, - UserNo = gainfoNo, - DeviceUniqueNo = x.UniqueNo, - Status = DeviceTaskStatusEnumType.Wait, - Version = 0, - ResultMessage = null, - CancellationId = 0, - Source = DeviceTaskSourceEnumType.Manually, - Priority = 0, - TenantId = x.TenantId, - }).ToList()); - } - - foreach (var items in tasks.Where(x => x.Type == DeviceTaskEnumType.Add).Chunk(500)) - { - await _dbContext.InsertAsync(items.ToList()); - } - - return new DevicePermissionAssignResponse - { - AddCount = addDevices.Count * gainfoNos.Count, - DeleteCount = deleteDevices.Count * gainfoNos.Count - }; - } - - private static void RecursionGetNextDeviceGroup(List allData, DeviceGroupEntity current, List result) - { - var nextItems = allData.Where(x => x.PCode == current.Code).ToList(); - foreach (var item in nextItems) - { - result.Add(item.Code); - RecursionGetNextDeviceGroup(allData, item, result); - } - } - - private async Task> GetDevicesByGroupsAsync(List allData, List groups) - { - var result = new List(); - foreach (var group in groups) - { - result.Add(group.Code); - RecursionGetNextDeviceGroup(allData, group, result); - } - - var deviceCodes = await _dbContext.Queryable() - .Where(x => result.Contains(x.GroupCode)) - .Select(x => x.DeviceCode) - .ToListAsync(); - - return await _dbContext.Queryable() - .Where(x => deviceCodes.Contains(x.Code)) - .ToListAsync(); + return await _namedResolver + .GetService(PermissionAnalyzeConstants.GetTypeName(request.AssignType)) + .AnalyzeAsync(request); } public async Task AssignToUniqueAsync(DevicePermissionsAssignToDeviceRequest request) @@ -475,10 +223,19 @@ public class DevicePermissionService : IDevicePermissionService } /// - public async Task>> GetUserDevicePermissionsAsync(string code) + public async Task>> GetUserDevicePermissionsAsync(string code) { var userNo = await _dbContext.Queryable().Where(x => x.Code == code).Select(x => x.No).SingleAsync(); - return await _devicePermissionAnalyzeService.GetAssignDeviceCodesInternalAsync(new List { userNo }); + var result = await _devicePermissionAnalyzeService.GetUserAssignDeviceCodesWithTypeInTenantAsync(new List { userNo }); + + return result.ToDictionary(x => x.Key, x => x.Value.GroupBy(p => p.Tenant).Select(item => + { + return new UserTenantDeviceCodeDto + { + Tenant = item.Key, + Codes = item.SelectMany(p => p.AssignTypes).SelectMany(p => p.Codes).Distinct().ToList(), + }; + })); } @@ -701,7 +458,7 @@ public class DevicePermissionService : IDevicePermissionService public async Task> GetAssignDeviceCodesAsync(string userCode) { var userNo = await _dbContext.Queryable().Where(x => x.Code == userCode || x.No == userCode).Select(x => x.No).SingleAsync(); - var result = await _devicePermissionAnalyzeService.GetAssignDeviceCodesInternalAsync(new List { userNo }); - return result.First().Value.SelectMany(x => x.Codes).ToList(); + var result = await _devicePermissionAnalyzeService.GetUserAssignDeviceCodesWithTypeInTenantAsync(new List { userNo }); + return result.First().Value.SelectMany(x => x.AssignTypes.SelectMany(p => p.Codes)).Distinct().ToList(); } } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Device/Services/Implements/ParallelService.cs b/Src/Dlhis.Basic/Device/Services/Implements/ParallelService.cs deleted file mode 100644 index 469b940d..00000000 --- a/Src/Dlhis.Basic/Device/Services/Implements/ParallelService.cs +++ /dev/null @@ -1,7 +0,0 @@ -namespace Dlhis.Basic.Device.Services.Implements; - -public class ParallelService : IParallelService -{ - /// - public bool Enable { get; set; } -} \ No newline at end of file diff --git a/Src/Dlhis.Basic/ObfuscateProviderJsonConverter.cs b/Src/Dlhis.Basic/ObfuscateProviderJsonConverter.cs index a76eb20c..59d1ec5d 100644 --- a/Src/Dlhis.Basic/ObfuscateProviderJsonConverter.cs +++ b/Src/Dlhis.Basic/ObfuscateProviderJsonConverter.cs @@ -1,7 +1,7 @@ using System.Security.Claims; using Kurisu.AspNetCore; using Kurisu.AspNetCore.Authentication.Abstractions; -using Kurisu.AspNetCore.Utils; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.Utils.Converters; using Newtonsoft.Json; diff --git a/Src/Dlhis.Basic/Organization/Dto/GainfoDto.cs b/Src/Dlhis.Basic/Organization/Dto/GainfoDto.cs index 177f1f0c..2e9b5f23 100644 --- a/Src/Dlhis.Basic/Organization/Dto/GainfoDto.cs +++ b/Src/Dlhis.Basic/Organization/Dto/GainfoDto.cs @@ -1,4 +1,6 @@ -namespace Dlhis.Basic.Organization.Dto; +using Dlhis.Entity.Sys.Enums; + +namespace Dlhis.Basic.Organization.Dto; public class GainfoDto { @@ -15,4 +17,17 @@ public class GainfoDto public bool IsOutsource { get; set; } public bool EnableFactoryPermission { get; set; } +} + +public class AnalyzePackDto +{ + public string UserNo { get; set; } + public string UserDepartment { get; set; } + public string UserFactory { get; set; } + + public IEnumerable UserGainfoGroupCodes { get; set; } + + public IEnumerable DeviceCodes { get; set; } + + public IEnumerable IgnoreAssignTypeTypes { get; set; } } \ No newline at end of file diff --git a/Src/Dlhis.Basic/Organization/Services/Implements/GainfoGroupService.cs b/Src/Dlhis.Basic/Organization/Services/Implements/GainfoGroupService.cs index 5cd582d7..dd195f8b 100644 --- a/Src/Dlhis.Basic/Organization/Services/Implements/GainfoGroupService.cs +++ b/Src/Dlhis.Basic/Organization/Services/Implements/GainfoGroupService.cs @@ -1,7 +1,11 @@ -using Dlhis.Basic.Device.Services; +using Dlhis.Basic.Device; +using Dlhis.Basic.Device.Request; +using Dlhis.Basic.Device.Services; using Dlhis.Basic.Organization.Request; using Dlhis.Basic.Organization.Response; using Dlhis.Entity.Basic.Entity; +using Dlhis.Entity.Sys.Entities; +using Dlhis.Entity.Sys.Enums; using Kurisu.AspNetCore.Authentication.Abstractions; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; using Kurisu.AspNetCore.Utils.Extensions; @@ -13,13 +17,13 @@ public class GainfoGroupService : IGainfoGroupService { private readonly IDbContext _dbContext; private readonly ICurrentUser _currentUser; - private readonly IDevicePermissionAnalyzeService _devicePermissionAnalyzeService; + private readonly INamedResolver _namedResolver; - public GainfoGroupService(IDbContext dbContext, ICurrentUser currentUser, IDevicePermissionAnalyzeService devicePermissionAnalyzeService) + public GainfoGroupService(IDbContext dbContext, ICurrentUser currentUser, INamedResolver namedResolver) { _dbContext = dbContext; _currentUser = currentUser; - _devicePermissionAnalyzeService = devicePermissionAnalyzeService; + _namedResolver = namedResolver; } public async Task> GetTreeAsync() @@ -82,28 +86,60 @@ public class GainfoGroupService : IGainfoGroupService var existsNextGroup = await _dbContext.Queryable().Where(x => x.PCode == request.GroupCode).AnyAsync(); existsNextGroup.ThrowIfTrue("存在下级分组,无法分配人员"); - await _devicePermissionAnalyzeService.GenerateDeviceTasksAsync(async () => + var relations = await _dbContext.Queryable() + .Where(x => x.GroupCode == request.GroupCode) + .ToListAsync(); + await _dbContext.DeleteAsync(relations); + + var userNos = await _dbContext.Queryable() + .Where(x => request.UserNos.Contains(x.No) || request.UserNos.Contains(x.Code)) //NO和工号匹配 + .Select(x => x.No) + .ToListAsync(); + + //(userNos.Count != request.UserNos.Count).ThrowIfTrue("存在权限外人员,无法添加"); + + var entities = userNos.Select(x => new GainfoGroupRelationshipEntity { - var relations = await _dbContext.Queryable() - .Where(x => x.GroupCode == request.GroupCode) - .ToListAsync(); - await _dbContext.DeleteAsync(relations); + GroupCode = request.GroupCode, + UserNo = x + }).ToList(); - var userNos = await _dbContext.Queryable() - .Where(x => request.UserNos.Contains(x.No) || request.UserNos.Contains(x.Code)) //NO和工号匹配 - .Select(x => x.No) - .ToListAsync(); + await _dbContext.InsertAsync(entities); - //(userNos.Count != request.UserNos.Count).ThrowIfTrue("存在权限外人员,无法添加"); + await PermissionResetAsync(request.GroupCode); + } - var entities = userNos.Select(x => new GainfoGroupRelationshipEntity + + private async Task PermissionResetAsync(Guid groupCode) + { + var gainfoGroups = RecursionHelper.HandlerGainfoGroupPreviousCodes(groupCode, await _dbContext.Queryable().ToListAsync()).Select(x => x.ToString()); + + var dps = await _dbContext.Queryable() + .Where(x => x.AssignType == AssignTypeEnumType.Group) + .Where(x => gainfoGroups.Contains(x.AssignValue)) + .ToListAsync(); + + var analyzeService = _namedResolver.GetService(PermissionAnalyzeConstants.GetTypeName(AssignTypeEnumType.Group)); + + foreach (var devicePermissionGroup in dps.GroupBy(x => new { x.AssignValue, x.TenantId, x.UniqueType, x.Type })) + { + var assignValue = devicePermissionGroup.Key.AssignValue; + var tenantId = devicePermissionGroup.Key.TenantId; + var uniqueType = devicePermissionGroup.Key.UniqueType; + var type = devicePermissionGroup.Key.Type; + + var codes = devicePermissionGroup.Select(x => x.UniqueValue).Distinct().ToList(); + + await analyzeService.AnalyzeAsync(new DevicePermissionSaveRequest { - GroupCode = request.GroupCode, - UserNo = x - }).ToList(); - - await _dbContext.InsertAsync(entities); - }, null); + AssignType = AssignTypeEnumType.Group, + AssignValue = assignValue, + UniqueType = uniqueType, + Codes = codes, + TenantId = tenantId, + Type = type + }); + } } diff --git a/Src/Dlhis.Basic/Organization/Services/Implements/GainfoOutsourceService.cs b/Src/Dlhis.Basic/Organization/Services/Implements/GainfoOutsourceService.cs index 1f1cc33b..775af9e6 100644 --- a/Src/Dlhis.Basic/Organization/Services/Implements/GainfoOutsourceService.cs +++ b/Src/Dlhis.Basic/Organization/Services/Implements/GainfoOutsourceService.cs @@ -3,8 +3,8 @@ using Dlhis.Basic.Organization.Response; using Dlhis.Entity.Basic.Entity; using Dlhis.Entity.Basic.Enums; using Dlhis.Entity.Device.Entities; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; -using Kurisu.AspNetCore.Utils; using Kurisu.AspNetCore.Utils.Extensions; using Mapster; using SqlSugar; diff --git a/Src/Dlhis.Basic/Program.cs b/Src/Dlhis.Basic/Program.cs index 882db25c..62899522 100644 --- a/Src/Dlhis.Basic/Program.cs +++ b/Src/Dlhis.Basic/Program.cs @@ -1,5 +1,5 @@ +using Kurisu.AspNetCore.Cache.Extensions; using Kurisu.AspNetCore.Startup; -using Kurisu.AspNetCore.Utils.Extensions; using Microsoft.IdentityModel.Logging; class Program diff --git a/Src/Dlhis.Basic/RecursionHelper.cs b/Src/Dlhis.Basic/RecursionHelper.cs index 9a953c94..cdee2661 100644 --- a/Src/Dlhis.Basic/RecursionHelper.cs +++ b/Src/Dlhis.Basic/RecursionHelper.cs @@ -106,4 +106,25 @@ public static class RecursionHelper } } } + + public static List HandlerDeviceGroupPreviousCodes(Guid current, List data) + { + var result = new List { current }; + + InternalHandlerCodes(current, data, result); + + return result; + + static void InternalHandlerCodes(Guid internalCurrent, List internalData, List internalResult) + { + var pno = internalData.FirstOrDefault(x => x.Code == internalCurrent)?.PCode; + if (!pno.HasValue) + { + return; + } + + internalResult.Add(pno.Value); + InternalHandlerCodes(pno.Value, internalData, internalResult); + } + } } \ No newline at end of file diff --git a/Src/Dlhis.Canteen/Order/Services/Implements/BalanceService.cs b/Src/Dlhis.Canteen/Order/Services/Implements/BalanceService.cs index 5a45ff2a..01da552b 100644 --- a/Src/Dlhis.Canteen/Order/Services/Implements/BalanceService.cs +++ b/Src/Dlhis.Canteen/Order/Services/Implements/BalanceService.cs @@ -12,6 +12,7 @@ using Dlhis.Entity.Device.Enums; using Dlhis.Sys.Api; using Kurisu.AspNetCore; using Kurisu.AspNetCore.Authentication.Abstractions; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.CustomClass; using Kurisu.AspNetCore.DataAccess.Dto; using Kurisu.AspNetCore.DataAccess.SqlSugar.Extensions; diff --git a/Src/Dlhis.Canteen/Order/Services/Implements/OrderService.cs b/Src/Dlhis.Canteen/Order/Services/Implements/OrderService.cs index 9bb02d33..caf30660 100644 --- a/Src/Dlhis.Canteen/Order/Services/Implements/OrderService.cs +++ b/Src/Dlhis.Canteen/Order/Services/Implements/OrderService.cs @@ -15,6 +15,7 @@ using Dlhis.Canteen.Order.Request; using Dlhis.Entity.Device; using Dlhis.Entity.Device.Enums; using Kurisu.AspNetCore.Authentication.Abstractions; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.CustomClass; using Kurisu.AspNetCore.DataAccess.Dto; using Kurisu.AspNetCore.DataAccess.SqlSugar.Extensions; diff --git a/Src/Dlhis.Canteen/Program.cs b/Src/Dlhis.Canteen/Program.cs index 8f18c30e..5f74bf3a 100644 --- a/Src/Dlhis.Canteen/Program.cs +++ b/Src/Dlhis.Canteen/Program.cs @@ -1,3 +1,4 @@ +using Kurisu.AspNetCore.Cache.Extensions; using Kurisu.AspNetCore.Startup; using Kurisu.AspNetCore.Utils.Extensions; using Microsoft.IdentityModel.Logging; diff --git a/Src/Dlhis.Entity/Dlhis.Entity.csproj b/Src/Dlhis.Entity/Dlhis.Entity.csproj index a8fefb58..c3f003b9 100644 --- a/Src/Dlhis.Entity/Dlhis.Entity.csproj +++ b/Src/Dlhis.Entity/Dlhis.Entity.csproj @@ -6,12 +6,12 @@ disable - - - - + + + + diff --git a/Src/Dlhis.Entity/SqlSugarPack.cs b/Src/Dlhis.Entity/SqlSugarPack.cs index 77ba0c10..82741972 100644 --- a/Src/Dlhis.Entity/SqlSugarPack.cs +++ b/Src/Dlhis.Entity/SqlSugarPack.cs @@ -15,7 +15,7 @@ public class SqlSugarPack : BaseAppPack { public override void ConfigureServices(IServiceCollection services) { - services.AddSqlSugar(sp => + services.AddSqlSugar(DbType.MySqlConnector, sp => { var configuration = sp.GetService(); @@ -80,7 +80,7 @@ public class SqlSugarPack : BaseAppPack }; }); } - + public override void Configure(IApplicationBuilder app, IWebHostEnvironment env) { var isGenerate = Configuration.GetSection("SqlSugarOptions").GetValue("Generate"); diff --git a/Src/Dlhis.External/Appointment/Services/Implements/AppointmentService.cs b/Src/Dlhis.External/Appointment/Services/Implements/AppointmentService.cs index 1860921a..fc523f0d 100644 --- a/Src/Dlhis.External/Appointment/Services/Implements/AppointmentService.cs +++ b/Src/Dlhis.External/Appointment/Services/Implements/AppointmentService.cs @@ -3,9 +3,9 @@ using Dlhis.Entity.Basic.Enums; using Dlhis.Entity.Visitor.Entity; using Dlhis.Entity.Visitor.Enums; using Dlhis.External.Appointment.Request; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.CustomClass; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; -using Kurisu.AspNetCore.Utils; using Kurisu.AspNetCore.Utils.Extensions; using SqlSugar; diff --git a/Src/Dlhis.External/Program.cs b/Src/Dlhis.External/Program.cs index c388c2a4..04c36cc8 100644 --- a/Src/Dlhis.External/Program.cs +++ b/Src/Dlhis.External/Program.cs @@ -1,6 +1,5 @@ -using Kurisu.AspNetCore.DataAccess.SqlSugar.Extensions; +using Kurisu.AspNetCore.Cache.Extensions; using Kurisu.AspNetCore.Startup; -using Kurisu.AspNetCore.Utils.Extensions; using Microsoft.IdentityModel.Logging; class Program diff --git a/Src/Dlhis.Middle/Services/Implements/OrderService.cs b/Src/Dlhis.Middle/Services/Implements/OrderService.cs index fadb172f..2928e0e8 100644 --- a/Src/Dlhis.Middle/Services/Implements/OrderService.cs +++ b/Src/Dlhis.Middle/Services/Implements/OrderService.cs @@ -69,7 +69,7 @@ public class OrderService : IOrderService var message = "离线消费:"; - gainfo.ThrowIfNull("无消费权限"); + gainfo.ThrowIfNull(message + "无消费权限"); var isError = false; try diff --git a/Src/Dlhis.ScheduledTask/BaseJob.cs b/Src/Dlhis.ScheduledTask/BaseJob.cs index 845ce16d..6fdd5974 100644 --- a/Src/Dlhis.ScheduledTask/BaseJob.cs +++ b/Src/Dlhis.ScheduledTask/BaseJob.cs @@ -1,8 +1,8 @@ using System.Reflection; using Dlhis.ScheduledTask.Attributes; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.DataAccess.Entity; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; -using Kurisu.AspNetCore.Utils; using Kurisu.Scheduled.Abstractions; namespace Dlhis.ScheduledTask; diff --git a/Src/Dlhis.ScheduledTask/Program.cs b/Src/Dlhis.ScheduledTask/Program.cs index 7c759046..1958c236 100644 --- a/Src/Dlhis.ScheduledTask/Program.cs +++ b/Src/Dlhis.ScheduledTask/Program.cs @@ -1,7 +1,5 @@ -using Dlhis.Jip.Api; -using Dlhis.Jip.Api.Request; +using Kurisu.AspNetCore.Cache.Extensions; using Kurisu.AspNetCore.Startup; -using Kurisu.AspNetCore.Utils.Extensions; class Program { diff --git a/Src/Dlhis.ScheduledTask/TaskAssignment/Controllers/HangfireController.cs b/Src/Dlhis.ScheduledTask/TaskAssignment/Controllers/HangfireController.cs index 9999cfff..e1c3a8ec 100644 --- a/Src/Dlhis.ScheduledTask/TaskAssignment/Controllers/HangfireController.cs +++ b/Src/Dlhis.ScheduledTask/TaskAssignment/Controllers/HangfireController.cs @@ -3,7 +3,7 @@ using Dlhis.Jip.Api; using Dlhis.Jip.Api.Request; using Dlhis.Jip.Api.Requests; using Hangfire; -using Kurisu.AspNetCore.Utils; +using Kurisu.AspNetCore.Cache; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; diff --git a/Src/Dlhis.Sys/Identity/Services/Implements/RoleService.cs b/Src/Dlhis.Sys/Identity/Services/Implements/RoleService.cs index 6f52900c..efef85c0 100644 --- a/Src/Dlhis.Sys/Identity/Services/Implements/RoleService.cs +++ b/Src/Dlhis.Sys/Identity/Services/Implements/RoleService.cs @@ -2,11 +2,11 @@ using Dlhis.Sys.Identity.Request; using Dlhis.Sys.Identity.Response; using Kurisu.AspNetCore.Authentication.Abstractions; +using Kurisu.AspNetCore.Cache; using Kurisu.AspNetCore.CustomClass; using Kurisu.AspNetCore.DataAccess.Dto; using Kurisu.AspNetCore.DataAccess.SqlSugar.Extensions; using Kurisu.AspNetCore.DataAccess.SqlSugar.Services; -using Kurisu.AspNetCore.Utils; using Kurisu.AspNetCore.Utils.Extensions; namespace Dlhis.Sys.Identity.Services.Implements; diff --git a/Src/Dlhis.Sys/Program.cs b/Src/Dlhis.Sys/Program.cs index e883ec6b..1f7ee7da 100644 --- a/Src/Dlhis.Sys/Program.cs +++ b/Src/Dlhis.Sys/Program.cs @@ -1,5 +1,5 @@ +using Kurisu.AspNetCore.Cache.Extensions; using Kurisu.AspNetCore.Startup; -using Kurisu.AspNetCore.Utils.Extensions; using Microsoft.IdentityModel.Logging; namespace Dlhis.Sys;