asp.net 带 cookie 中间件的核心 - 在授权时访问请求数据
asp.net core w/ cookie middleware - accessing request data on authorization
这个问题本质上与 here 相同,但是,对于 asp.net 核心,同时使用 asp.net 核心 cookie 中间件。
是否可以在验证时访问查询 string/request 正文数据,如果可以,您会鼓励这个想法吗?似乎根据 this 这很有可能,但是,来自大男孩 asp.net 的规则是否相同(例如您只能在给定的请求生命周期内读取一次请求数据)?
示例:我正在创建一个应用程序,其中人们拥有一个帐户,但他们是不同团队的成员。他们可以在应用程序中执行许多不同的操作,并且,他们可以在他们所属的一个或另一个团队的 "context" 中执行该操作。因此,我在向服务器发出的请求中传递了一个 teamId 整数。我想从 ClaimsPrincipal 中提取声明,以验证他们确实是管道授权部分中该团队的成员。
正如您所说,可以在 OnValidatePrincipal
事件中访问请求的数据。所以,你可以这样写:
OnValidatePrincipal = async (context) =>
{
if (context.Request.Path.Value.StartsWith("/teams/"))
{
var teamId = // get team id from Path;
if (user is not team member)
{
context.Response.StatusCode = 403;
}
}
}
但是, 我认为您的要求与 Authorization
有关,而不是 Authentication
。我会使用 Policy-Based Authorization
来处理需求。政策示例应如下所示:
要求和处理程序:
public class TeamMemberHandler: AuthorizationHandler<TeamMemberRequirement>
{
private readonly IActionContextAccessor _accessor; // for getting teamId from RouteData
public TeamMemberHandler(IActionContextAccessor accessor)
{
_accessor = accessor;
}
protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, TeamMemberRequirement requirement)
{
var teamId = // get teamId with using _accessor
if (user is not member of team(by teamId))
{
context.Fail();
}
return Task.FromResult(0);
}
}
public class TeamMemberRequirement : IAuthorizationRequirement
{
}
配置服务:
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
services.AddSingleton<IActionContextAccessor, ActionContextAccessor>();
services.AddAuthorization(options =>
{
options.AddPolicy("TeamMember",
policy => policy.Requirements.Add(new TeamMemberRequirement()));
});
services.AddSingleton<IAuthorizationHandler, TeamMemberHandler>();
}
最后在控制器之上使用它(或者如果你愿意,你可以在全局添加过滤器)
Authorize[(Policy = "TeamMember")]
public class TeamHomeController : Controller
{
// Authorize[(Policy = "AnotherPolicy")]
public IActionResult Index(){}
}
这个问题本质上与 here 相同,但是,对于 asp.net 核心,同时使用 asp.net 核心 cookie 中间件。
是否可以在验证时访问查询 string/request 正文数据,如果可以,您会鼓励这个想法吗?似乎根据 this 这很有可能,但是,来自大男孩 asp.net 的规则是否相同(例如您只能在给定的请求生命周期内读取一次请求数据)?
示例:我正在创建一个应用程序,其中人们拥有一个帐户,但他们是不同团队的成员。他们可以在应用程序中执行许多不同的操作,并且,他们可以在他们所属的一个或另一个团队的 "context" 中执行该操作。因此,我在向服务器发出的请求中传递了一个 teamId 整数。我想从 ClaimsPrincipal 中提取声明,以验证他们确实是管道授权部分中该团队的成员。
正如您所说,可以在 OnValidatePrincipal
事件中访问请求的数据。所以,你可以这样写:
OnValidatePrincipal = async (context) =>
{
if (context.Request.Path.Value.StartsWith("/teams/"))
{
var teamId = // get team id from Path;
if (user is not team member)
{
context.Response.StatusCode = 403;
}
}
}
但是, 我认为您的要求与 Authorization
有关,而不是 Authentication
。我会使用 Policy-Based Authorization
来处理需求。政策示例应如下所示:
要求和处理程序:
public class TeamMemberHandler: AuthorizationHandler<TeamMemberRequirement>
{
private readonly IActionContextAccessor _accessor; // for getting teamId from RouteData
public TeamMemberHandler(IActionContextAccessor accessor)
{
_accessor = accessor;
}
protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, TeamMemberRequirement requirement)
{
var teamId = // get teamId with using _accessor
if (user is not member of team(by teamId))
{
context.Fail();
}
return Task.FromResult(0);
}
}
public class TeamMemberRequirement : IAuthorizationRequirement
{
}
配置服务:
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
services.AddSingleton<IActionContextAccessor, ActionContextAccessor>();
services.AddAuthorization(options =>
{
options.AddPolicy("TeamMember",
policy => policy.Requirements.Add(new TeamMemberRequirement()));
});
services.AddSingleton<IAuthorizationHandler, TeamMemberHandler>();
}
最后在控制器之上使用它(或者如果你愿意,你可以在全局添加过滤器)
Authorize[(Policy = "TeamMember")]
public class TeamHomeController : Controller
{
// Authorize[(Policy = "AnotherPolicy")]
public IActionResult Index(){}
}