09获取权限源码阅读记录
类关系图
属于Volo.Abp解决方案的类:
PermissionDefinitionManager
属于Volo.Abp.PermissionManagement解决方案的类:
PermissionsController
PermissionAppService
PermissionManager
PermissionManagementProvider
EfCorePermissionGrantRepository
属于Volo.Abp.Identity解决方案的类:
UserPermissionManagementProvider
RolePermissionManagementProvider
PermissionDefinitionManage
用于提供系统中定义的权限定义
PermissionManager
权限管理类
获取权限方法:
public virtual async Task<MultiplePermissionWithGrantedProviders> GetAsync(
string[] permissionNames,
string providerName,
string providerKey)
{
var permissions = new List<PermissionDefinition>();
var undefinedPermissions = new List<string>();
// 获取并检查系统定义的权限
foreach (var permissionName in permissionNames)
{
var permission = await PermissionDefinitionManager.GetOrNullAsync(permissionName);
if (permission != null)
{
permissions.Add(permission);
}
else
{
undefinedPermissions.Add(permissionName);
}
}
if (!permissions.Any())
{
return new MultiplePermissionWithGrantedProviders(undefinedPermissions.ToArray());
}
// 检查权限是否授予
var result = await GetInternalAsync(
permissions.ToArray(),
providerName,
providerKey
);
foreach (var undefinedPermission in undefinedPermissions)
{
result.Result.Add(new PermissionWithGrantedProviders(undefinedPermission, false));
}
return result;
}
protected virtual async Task<MultiplePermissionWithGrantedProviders> GetInternalAsync(
PermissionDefinition[] permissions,
string providerName,
string providerKey)
{
var permissionNames = permissions.Select(x => x.Name).ToArray();
var multiplePermissionWithGrantedProviders = new MultiplePermissionWithGrantedProviders(permissionNames);
var neededCheckPermissions = new List<PermissionDefinition>();
foreach (var permission in permissions
.Where(x => x.IsEnabled)
.Where(x => x.MultiTenancySide.HasFlag(CurrentTenant.GetMultiTenancySide()))
.Where(x => !x.Providers.Any() || x.Providers.Contains(providerName)))
{
if (await SimpleStateCheckerManager.IsEnabledAsync(permission))
{
neededCheckPermissions.Add(permission);
}
}
if (!neededCheckPermissions.Any())
{
return multiplePermissionWithGrantedProviders;
}
// 关键代码 循环调用系统所有权限管理提供程序的 CheckAsync 方法
foreach (var provider in ManagementProviders)
{
permissionNames = neededCheckPermissions.Select(x => x.Name).ToArray();
var multiplePermissionValueProviderGrantInfo = await provider.CheckAsync(permissionNames, providerName, providerKey);
// 处理结果
foreach (var providerResultDict in multiplePermissionValueProviderGrantInfo.Result)
{
if (providerResultDict.Value.IsGranted)
{
var permissionWithGrantedProvider = multiplePermissionWithGrantedProviders.Result
.First(x => x.Name == providerResultDict.Key);
permissionWithGrantedProvider.IsGranted = true;
permissionWithGrantedProvider.Providers.Add(new PermissionValueProviderInfo(provider.Name, providerResultDict.Value.ProviderKey));
}
}
}
return multiplePermissionWithGrantedProviders;
}
PermissionManagementProvider
用于检查是否拥有权限,设置权限的基类
检查权限源码
/// <summary>
/// 检查权限
/// </summary>
/// <param name="names">需要检查的权限名</param>
/// <param name="providerName">权限管理提供名称</param>
/// <param name="providerKey">需要检查权限的用户ID或用户组ID或其他需要检查权限的ID</param>
/// <returns></returns>
public virtual async Task<MultiplePermissionValueProviderGrantInfo> CheckAsync(string[] names, string providerName, string providerKey)
{
var multiplePermissionValueProviderGrantInfo = new MultiplePermissionValueProviderGrantInfo(names);
if (providerName != Name)
{
return multiplePermissionValueProviderGrantInfo;
}
// 从资源库中获取 providerKey 拥有的权限
var permissionGrants = await PermissionGrantRepository.GetListAsync(names, providerName, providerKey);
foreach (var permissionName in names)
{
var isGrant = permissionGrants.Any(x => x.Name == permissionName);
multiplePermissionValueProviderGrantInfo.Result[permissionName] = new PermissionValueProviderGrantInfo(isGrant, providerKey);
}
return multiplePermissionValueProviderGrantInfo;
}
UserPermissionManagementProvider
用户权限管理提供程序,继承PermissionManagementProvider
基类
RolePermissionManagementProvider
角色权限管理提供程序,继承PermissionManagementProvider
基类,重写了CheckAsync
方法
public override async Task<MultiplePermissionValueProviderGrantInfo> CheckAsync(string[] names, string providerName, string providerKey)
{
var multiplePermissionValueProviderGrantInfo = new MultiplePermissionValueProviderGrantInfo(names);
var permissionGrants = new List<PermissionGrant>();
// 如果是获取用户角色的权限,则直接从资源库中获取用户角色已授权权限
if (providerName == Name)
{
permissionGrants.AddRange(await PermissionGrantRepository.GetListAsync(names, providerName, providerKey));
}
// 如果是获取用户的权限,则获取用户所属用户角色的权限
if (providerName == UserPermissionValueProvider.ProviderName)
{
var userId = Guid.Parse(providerKey);
var roleNames = await UserRoleFinder.GetRolesAsync(userId);
foreach (var roleName in roleNames)
{
permissionGrants.AddRange(await PermissionGrantRepository.GetListAsync(names, Name, roleName));
}
}
// 以下是处理返回结果
permissionGrants = permissionGrants.Distinct().ToList();
if (!permissionGrants.Any())
{
return multiplePermissionValueProviderGrantInfo;
}
foreach (var permissionName in names)
{
var permissionGrant = permissionGrants.FirstOrDefault(x => x.Name == permissionName);
if (permissionGrant != null)
{
multiplePermissionValueProviderGrantInfo.Result[permissionName] = new PermissionValueProviderGrantInfo(true, permissionGrant.ProviderKey);
}
}
return multiplePermissionValueProviderGrantInfo;
}
当通过 /api/permission-management/permissions?providerName=U&providerKey=XXXX
获取用户权限时,系统通过执行UserPermissionManagementProvider
的CheckAsync
方法获取用户被授予的权限,并通过执行RolePermissionManagementProvider
的CheckAsync
方法获取用户拥有用户角色的权限。
自定义权限规则
添加权限值提供类
在Domain
层添加CustomPermissionValueProvider.cs
继承PermissionValueProvider
类,处理权限值的验证
public class CustomPermissionValueProvider : PermissionValueProvider
{
public CustomPermissionValueProvider(IPermissionStore permissionStore) : base(permissionStore)
{
}
public const string ProviderName = "Z";
public override string Name => ProviderName;
public override async Task<PermissionGrantResult> CheckAsync(PermissionValueCheckContext context)
{
var userId = context.Principal?.FindFirst(AbpClaimTypes.UserId)?.Value;
if (userId == null)
{
return PermissionGrantResult.Undefined;
}
return await PermissionStore.IsGrantedAsync(context.Permission.Name, Name, userId)
? PermissionGrantResult.Granted
: PermissionGrantResult.Undefined;
}
public override async Task<MultiplePermissionGrantResult> CheckAsync(PermissionValuesCheckContext context)
{
var permissionNames = context.Permissions.Select(x => x.Name).Distinct().ToArray();
Check.NotNullOrEmpty(permissionNames, nameof(permissionNames));
var userId = context.Principal?.FindFirst(AbpClaimTypes.UserId)?.Value;
if (userId == null)
{
return new MultiplePermissionGrantResult(permissionNames);
}
return await PermissionStore.IsGrantedAsync(permissionNames, Name, userId);
}
}
添加权限管理提供类
在Domain
层添加CustomPermissionManagementProvider
继承PermissionManagementProvider
类,并重写CheckAsync
方法,定义自己的权限验证方式
public class CustomPermissionManagementProvider : PermissionManagementProvider
{
// 这里的name与CustomPermissionValueProvider中的ProviderName保持一致
public override string Name => "Z";
public CustomPermissionManagementProvider(
IPermissionGrantRepository permissionGrantRepository,
IGuidGenerator guidGenerator,
ICurrentTenant currentTenant)
: base(
permissionGrantRepository,
guidGenerator,
currentTenant)
{
}
public override async Task<PermissionValueProviderGrantInfo> CheckAsync(string name, string providerName, string providerKey)
{
var multipleGrantInfo = await CheckAsync(new[] { name }, providerName, providerKey);
return multipleGrantInfo.Result.Values.First();
}
public override async Task<MultiplePermissionValueProviderGrantInfo> CheckAsync(string[] names, string providerName, string providerKey)
{
var multiplePermissionValueProviderGrantInfo = new MultiplePermissionValueProviderGrantInfo(names);
var permissionGrants = new List<PermissionGrant>();
// 如果是自定义的权限类型获取权限,则从资源库中获取权限
if (providerName == Name)
{
permissionGrants.AddRange(await PermissionGrantRepository.GetListAsync(names, providerName, providerKey));
}
// 如果是处理用户的权限,则该提供类赋予用户所有权限
if (providerName == UserPermissionValueProvider.ProviderName)
{
foreach (var name in names) {
permissionGrants.Add(new PermissionGrant(GuidGenerator.Create(),name,Name,"测试自定义权限"));
}
}
// 以下处理返回结果
permissionGrants = permissionGrants.Distinct().ToList();
if (!permissionGrants.Any())
{
return multiplePermissionValueProviderGrantInfo;
}
foreach (var permissionName in names)
{
var permissionGrant = permissionGrants.FirstOrDefault(x => x.Name == permissionName);
if (permissionGrant != null)
{
multiplePermissionValueProviderGrantInfo.Result[permissionName] = new PermissionValueProviderGrantInfo(true, permissionGrant.ProviderKey);
}
}
return multiplePermissionValueProviderGrantInfo;
}
}
配置自定义权限规则
在DomainModule
的ConfigureServices
方法中添加自定义的权限规则配置
Configure<AbpPermissionOptions>(options =>
{
options.ValueProviders.Add<CustomPermissionValueProvider>();
});
Configure<PermissionManagementOptions>(options =>
{
options.ManagementProviders.Add<CustomPermissionManagementProvider>();
options.ProviderPolicies.Add(CustomPermissionValueProvider.ProviderName, "AbpIdentity.Users.ManagePermissions");
});
如此完成自定义权限规则
Api返回JSON
{
"entityDisplayName": "62a4b9b6-161e-6b1f-ccbe-3a0aa43a2249",
"groups": [{
"name": "AbpIdentity",
"displayName": "身份标识管理",
"permissions": [{
"name": "AbpIdentity.Roles",
"displayName": "角色管理",
"parentName": null,
"isGranted": true,
"allowedProviders": [],
"grantedProviders": [{
"providerName": "R",
"providerKey": "admin"
}, {
"providerName": "Z",
"providerKey": "测试自定义权限"
}]
}, {
"name": "AbpIdentity.Roles.Create",
"displayName": "创建",
"parentName": "AbpIdentity.Roles",
"isGranted": true,
"allowedProviders": [],
"grantedProviders": [{
"providerName": "R",
"providerKey": "admin"
}, {
"providerName": "Z",
"providerKey": "测试自定义权限"
}]
},
...]
}, {
"name": "PurchaseManage",
"displayName": "采购管理",
"permissions": [{
"name": "PurchaseManage.PruchaseOrder",
"displayName": "采购订单",
"parentName": null,
"isGranted": true,
"allowedProviders": [],
"grantedProviders": [{
"providerName": "U",
"providerKey": "62a4b9b6-161e-6b1f-ccbe-3a0aa43a2249"
}, {
"providerName": "Z",
"providerKey": "测试自定义权限"
}]
},
...]
}]
}