我正在尝试实施一项非常细粒度的政策。
这个想法就像图中一样。
每个实体始终具有一对多与右侧实体的关系。
一机构可以有很多Courses, each Course可以有很多Subjects, each Subject可以有很多Syllabus, etc...
有 3 个角色:Administrator
, Contributor
, Viewer
如果您在顶级实体之一拥有角色,则该角色将传播到下面的其余实体。
例如:如果您是课程管理员,那么您就是科目、教学大纲等的管理员...
如果您是课程大纲之一的贡献者,您将成为本课程大纲的以下课程和视频的贡献者。
我尝试使用解决它Custom Policies
:
添加如下要求:
public class AdministratorRequirement : IAuthorizationRequirement
{
public int UserId { get; private set; }
public EntityType EntityType { get; private set; }
public int EntityId { get; private set; }
public AdministratorRequirement(int userId, EntityType entityType, int entityId)
{
UserId = userId;
EntityType = entityType;
EntityId = entityId;
}
}
并添加策略处理程序,如下所示:
public class AdministratorHandler : AuthorizationHandler<AdministratorRequirement>
{
public IRolesRepository RolesRepository {get;set;}
public AdministratorHandler(IRolesRepository rolesRepository)
{
RolesRepository = rolesRepository;
}
protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, AdministratorRequirement requirement)
{
// Save User object to access claims
bool isAdministrator = RolesRepository.CheckUserRole(requirement.UserId, requirement.EntityType, requirement.EntityId, "Administrator");
if (isAdministrator)
context.Succeed(requirement);
return Task.CompletedTask;
}
}
问题是我想在 Startup 类上定义变量要求:
options.AddPolicy("CourseAdministrator",
policy => policy
.Requirements
.Add(
new AdministratorRequirement(
/*userId - should be variable*/ 0,
EntityType.Course,
/*int entityId - should be variable*/ 0))
并将其用在类似的东西上
[Authorize(/*pass some parameters in here like user Id and course Id*/)]
[HttpPost]
[Route("create")]
public async Task<IActionResult> CreateCourse([FromBody] Course course)
{
//Or call the policy handler programatically in here.
CleanCacheOnUpdateCourse();
return Ok(await Services.CreateCourse(course, EmauaUser));
}
不知道有没有这样的解决方案呢?