本文介绍了有没有一种方法可以将请求标头指定为ASP.NET Core Controller操作参数/参数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!
问题描述
我有如下控制器操作:
[ApiController]
[ApiVersion("1.0")]
[Route("api/v{version:apiVersion}")]
public class StuffController : ControllerBase
{
[HttpGet("stuff/")]
[Authorize(Roles = "admin,read-stuff")]
[Produces("application/json")]
[ProducesResponseType(typeof(IActionResult), StatusCodes.Status200OK)]
[ProducesResponseType(StatusCodes.Status401Unauthorized)]
[ProducesResponseType(StatusCodes.Status403Forbidden)]
public async Task<IActionResult> Get()
{
var authorization = Request.Headers["authorization"];
var accessToken = authorization[0].Replace("Bearer ", string.Empty);
// use accessToken for token exchange
// use the new token another to get and return the actual results
}
}
我想知道是否有一个技巧可以像操作参数中那样直接使用承载/访问令牌,例如:
I was wondering is there was a trick to have the bearer / access token directly available as in the action parameter, something like:
[ApiController]
[ApiVersion("1.0")]
[Route("api/v{version:apiVersion}")]
public class StuffController : ControllerBase
{
[HttpGet("stuff/")]
[Authorize(Roles = "admin,read-stuff")]
[Produces("application/json")]
[ProducesResponseType(typeof(IActionResult), StatusCodes.Status200OK)]
[ProducesResponseType(StatusCodes.Status401Unauthorized)]
[ProducesResponseType(StatusCodes.Status403Forbidden)]
public async Task<IActionResult> Get([BearerTokenHeader] string bearerTokenHeader)
{
// use accessToken for token exchange
// use the new token another to get and return the actual results
}
}
推荐答案
添加自定义属性,值提供者:
Add custom attribute, value provider:
[AttributeUsage(AttributeTargets.Parameter | AttributeTargets.Property, AllowMultiple = false, Inherited = true)]
public class BearerTokenFromHeaderAttribute : Attribute, IBindingSourceMetadata, IModelNameProvider
{
public BindingSource BindingSource => BearerTokenBindingSource.Instance;
public string Name { get; set; }
}
public static class BearerTokenBindingSource
{
public static readonly BindingSource Instance = new BindingSource(
"BearerToken",
"BearerToken",
isGreedy: false,
isFromRequest: true);
}
public class BearerTokenValueProviderFactory : IValueProviderFactory
{
public Task CreateValueProviderAsync(ValueProviderFactoryContext context)
{
var authorizationHeader = context.ActionContext.HttpContext.Request.Headers["Authorization"];
var accessToken = authorizationHeader[0].Replace("Bearer ", string.Empty);
context.ValueProviders.Add(new BearerTokenValueProvider(BearerTokenBindingSource.Instance, accessToken));
return Task.CompletedTask;
}
}
public class BearerTokenValueProvider : BindingSourceValueProvider
{
public BearerTokenValueProvider(BindingSource bindingSource, string accessToken) : base(bindingSource)
{
AccessToken = accessToken;
}
private string AccessToken { get; }
public override bool ContainsPrefix(string prefix)
{
return false;
}
public override ValueProviderResult GetValue(string key)
{
return new ValueProviderResult(AccessToken);
}
}
Startup.cs
Startup.cs
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
services.AddMvc(options =>
{
options.ValueProviderFactories.Add(new BearerTokenValueProviderFactory());
});
}
控制器
[ApiController]
[ApiVersion("1.0")]
[Route("api/v{version:apiVersion}")]
public class StuffController : ControllerBase
{
[HttpGet("stuff/")]
[Authorize(Roles = "admin,read-stuff")]
[Produces("application/json")]
[ProducesResponseType(typeof(IActionResult), StatusCodes.Status200OK)]
[ProducesResponseType(StatusCodes.Status401Unauthorized)]
[ProducesResponseType(StatusCodes.Status403Forbidden)]
public async Task<IActionResult> Get([BearerTokenFromHeader] string accessToken)
{
// use accessToken for token exchange
// use the new token another to get and return the actual results
}
}
这篇关于有没有一种方法可以将请求标头指定为ASP.NET Core Controller操作参数/参数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!