正在身份验证筛选器中ChallengeSync方法的上下文中设置Result



这个问题与我在这里提供的答案有关。OP的评论让我思考了一下。我建议在身份验证过滤器的ChallengeAsync方法中使用这样一个实现IHttpActionResult的类。

public Task ChallengeAsync(HttpAuthenticationChallengeContext context,
CancellationToken cancellationToken)
{
context.Result = new ResultWithChallenge(context.Result);
return Task.FromResult(0);
}
public class ResultWithChallenge : IHttpActionResult
{
private readonly IHttpActionResult next;
public ResultWithChallenge(IHttpActionResult next)
{
this.next = next;
}
public async Task<HttpResponseMessage> ExecuteAsync(
CancellationToken cancellationToken)
{
var response = await next.ExecuteAsync(cancellationToken);
if (response.StatusCode == HttpStatusCode.Unauthorized)
{
response.Headers.WwwAuthenticate.Add(
new AuthenticationHeaderValue("Basic", "realm=localhost"));
}
return response;
}
}

相反,我可以像这样简化ChallengeAsync

public Task ChallengeAsync(HttpAuthenticationChallengeContext context,
CancellationToken cancellationToken)
{
var result = await context.Result.ExecuteAsync(cancellationToken);
if (result.StatusCode == HttpStatusCode.Unauthorized)
{
result.Headers.WwwAuthenticate.Add(
new AuthenticationHeaderValue("Basic", "realm=localhost"));
}
context.Result = new ResponseMessageResult(result);
}

这使我不用创建实现IHttpActionResult的类,但这是正确的方法吗?我有一种不安的感觉,从性能的角度来看,这在某种程度上是糟糕的,因为感觉我正在将操作结果转换为HttpResponseMessage并返回到操作结果。任何关于这里需要一个单独的类来实现IHttpActionResult(如我所建议的)的指针都将被理解为不使用上面的代码。

目的是使用第一种方法而不是第二种方法。例如,请参阅基本身份验证示例(也可用于MVC),它遵循第一种方法:http://aspnet.codeplex.com/SourceControl/latest#Samples/WebApi/BasicAuthentication/ReadMe.txt

第二种方法基本有效。我不会太在意表现的观点;无论哪种方式,您都会分配一个操作结果对象和一个响应消息对象,所以我看不出有多大区别。

然而,我推荐第一种方法有几个原因:

  1. 第二种方法在MVC中的工作方式不同。MVC和Web API都有身份验证过滤器,它们的工作方式基本相同。但在MVC中,没有等效的ResponseMessageResult(HttpContext会根据需要更新,而不是返回一个HttpResponseMessage,该消息可以由堆栈中的每个调用方替换)。如果您有一个身份验证过滤器的MVC实现,那么您很可能最终会采用第一种方法
  2. 它稍微改变了管道的行为。ChallengeSync中的代码比上下文中的代码运行得更早。返回的结果。例如,如果代码更改了HttpRequestMessage上的一个属性,并影响了稍后过滤器的ChallengeSync逻辑,则行为可能与预期不同

该框架无疑可以使接口的实现更加容易;请随意就以下工作项目进行投票:https://aspnetwebstack.codeplex.com/workitem/1456

最新更新