C# 如何覆盖[ValidateAntiForgeryToken]返回的响应或手动验证令牌?
如果我对API方法使用C# 如何覆盖[ValidateAntiForgeryToken]返回的响应或手动验证令牌?,c#,asp.net-core,antiforgerytoken,C#,Asp.net Core,Antiforgerytoken,如果我对API方法使用[ValidateAntiForgeryToken]属性,我将获得自动生成的HTTP400 JSON。我希望能够编写JSON内容。我是否可以手动决定对验证问题的响应 我实现了我自己的: public class ExceptionFilteraaAttribute : ActionFilterAttribute { public override void OnActionExecuting(ActionExecutingContext context) {
[ValidateAntiForgeryToken]
属性,我将获得自动生成的HTTP400 JSON。我希望能够编写JSON内容。我是否可以手动决定对验证问题的响应
我实现了我自己的:
public class ExceptionFilteraaAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext context)
{
System.Console.WriteLine(context);
}
public override void OnActionExecuted(ActionExecutedContext context)
{
if (context?.Exception != null)
{
context.Result = new ObjectResult(...)
{
StatusCode = (int)HttpStatusCode.InternalServerError,
};
context.ExceptionHandled = true;
}
}
}
但是它永远不会到达这个地方,因为它已经响应了请求
我需要实施:
public class ChangedAntiforgeryResultFilter : ResultFilterAttribute
{
public override void OnResultExecuting(ResultExecutingContext context)
{
//this is never hit
if (context?.Result is AntiforgeryValidationFailedResult)
{
context.Result = new BadRequestObjectResult(new LoginErrorResponseDto
{
OperationId = context.HttpContext.Features?.Get<RequestTelemetry>()?.Context?.Operation?.Id
});
}
}
public override void OnResultExecuted(ResultExecutedContext context)
{
}
myChangedAntiForgeryResultFilter
从未访问过,400将返回default内容。您可以通过复制默认值,替换它生成的结果来构建自己的授权筛选器。一种不需要您重新实现验证逻辑的更简单的方法是,除了默认的[ValidateAntiForgeryToken]
之外,添加一个结果过滤器,用于检查AntiforgeryValidationFailedResult
并用其他内容替换它。这样的过滤器看起来很简单,如下所示:
公共类更改DantifOrgeryResultFilter:IAlwaysRunSultFilter
{
ResultExecuting上的公共void(ResultExecutingContext)
{
if(context.Result为AntiforgeryValidationFailedResult)
{
context.Result=新的StatusCodeResult(500);
}
}
ResultExecuted上的公共无效(ResultExecutedContext)
{ }
}
[HttpPost]
[ValidateAntiForgeryToken]
[TypeFilter(typeof(ChangedAntiforgeryResultFilter))]
公共IActionResult ExampleAction(ExampleModel模型)
=>视图(模型);
尽管如此,我不建议更改响应代码。响应代码的定义非常精确。4xx错误表示存在客户端错误,而5xx错误表示存在服务器错误。客户端未发送正确的防伪令牌在很大程度上是客户端错误。在这种情况下返回一个值是错误的
来自AntiforgeryValidationFailedResult
的默认响应是a,这是此处的正确结果:
400(错误请求)状态代码表示服务器无法或将不会处理请求,原因是被认为是客户端错误(例如,格式错误的请求语法、无效的请求消息帧或欺骗性的请求路由)
谢谢你的回答。我不想更改任何代码,只想用任何4xx/5xx只返回
operationId
,但同时我不想改变应用程序中其他API控制器的任何行为。我得到的错误是context。Result
是只读的,它只有getter。@Yoda Oops,我的坏,您需要实现OnResultExecuting方法。我纠正了我的错误code@Yoda我猜我错了,您无法覆盖从授权筛选器返回的结果:/。很抱歉。不幸的是,ValidateAntiforgeryTokenAuthorizationFilter
是内部的,因此您不能仅仅从中继承,而是需要自己滚动:/哦,对了,我忘了这个。让我自己试试,看看这里发生了什么。
[ValidateAntiForgeryToken]
[ChangedAntiforgeryResultFilter]