在 NET46 上使用 ASP.NET5 Web API 而没有 System.Web.Helpers 的防伪令牌
AntiForgery Token using ASP.NET5 Web API without System.Web.Helpers on NET46
尝试在 ASP.NET5 (又名 vNext) API
上实施防伪
我找到的所有文章都来自this article并使用System.Web.Helpers.AntiForgery.GetTokens这不应该是ASP.NET5[的方式
private static string GetTokenHeaderValue()
{
string cookieToken, formToken;
System.Web.Helpers.AntiForgery.GetTokens(null, out cookieToken, out formToken);
return cookieToken + ":" + formToken;
}
是否有任何实现实际显示如何在 ASP.NET5
中检索这些令牌
在控制器生成
using Microsoft.AspNet.Mvc;
using Microsoft.Framework.DependencyInjection;
namespace MyApp.App.Controllers
{
public class MyController : Controller
{
public string GetAntiForgeryTokens()
{
var antiForgery = Context.RequestServices.GetService<AntiForgery>();
AntiForgeryTokenSet antiForgeryTokenSet = antiForgery.GetTokens(Context, null);
string output = antiForgeryTokenSet.CookieToken + ":" + antiForgeryTokenSet.FormToken;
return output;
}
}
}
在查看时生成
@inject AntiForgery antiForgery
@functions
{
public string GetAntiForgeryTokens()
{
AntiForgeryTokenSet antiForgeryTokenSet = antiForgery.GetTokens(Context, null);
string output = antiForgeryTokenSet.CookieToken + ":" + antiForgeryTokenSet.FormToken;
return output;
}
}
<body>
@GetAntiXsrfToken()
</body>
验证
var antiForgery = Context.RequestServices.GetService<AntiForgery>();
antiForgery.Validate(Context, new AntiForgeryTokenSet(formToken, cookieToken));
使用 MVC 实现此目的的另一种方法是使用 HTML 帮助程序在创建 cookie 和隐藏输入字段令牌的视图上获取令牌。
<form>
@Html.AntiForgeryToken()
</form>
HTML 输出:
<input name="__RequestVerificationToken" type="hidden" value="*** />
现在表单令牌已经存在,我们可以在 header 中发送令牌或将其添加到 API 期望的模型中。 API 可以使用处理自定义防伪令牌验证的 ActionFilter 进行保护。类似于 [Authorize] 的工作方式
[ValidateAntiForgeryToken]
public class MyController : ApiController
逻辑是读取 headers,其中可以找到 cookie 和 header 值标记。然后可以使用对
的调用对其进行评估
AntiForgery.Validate(cookieToken, headerToken);
然后过滤器可以接受或拒绝请求。
拒绝返回:
HttpStatusCode.Forbidden
现在有 sample in the source code。该示例使用 Angular 1.x。在该示例的基础上,通过使用 Filter 进行验证,这是一个粗略的示例。在 Startup
需要设置令牌:
public void Configure(IApplicationBuilder app, IAntiforgery antiforgery)
{
app.Use(next => context =>
{
if (!context.Request.Path.Value.StartsWith("/api/"))
{
// We can send the request token as a JavaScript-readable cookie, and Angular will use it by default.
var tokens = antiforgery.GetAndStoreTokens(context);
context.Response.Cookies.Append("XSRF-TOKEN", tokens.RequestToken, new CookieOptions() { HttpOnly = false });
}
return next(context);
});
…
}
然后可以使用过滤器来验证令牌:
public class AntiforgeryValidationFilter : IAsyncActionFilter
{
private readonly IAntiforgery antiforgery;
public AntiforgeryValidationFilter(IAntiforgery antiforgery)
{
this.antiforgery = antiforgery;
}
public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
{
if (context.HttpContext.Request.Path.Value.StartsWith("/api/"))
{
await antiforgery.ValidateRequestAsync(context.HttpContext);
}
await next();
}
}
然后在Startup
中注册过滤器:
public void ConfigureServices(IServiceCollection services)
{
// Angular's default header name for sending the XSRF token.
services.AddAntiforgery(options => options.HeaderName = "X-XSRF-TOKEN");
services
.AddMvc(options =>
options.Filters.Add(typeof(AntiforgeryValidationFilter)))
…
}
尝试在 ASP.NET5 (又名 vNext) API
上实施防伪我找到的所有文章都来自this article并使用System.Web.Helpers.AntiForgery.GetTokens这不应该是ASP.NET5[的方式
private static string GetTokenHeaderValue()
{
string cookieToken, formToken;
System.Web.Helpers.AntiForgery.GetTokens(null, out cookieToken, out formToken);
return cookieToken + ":" + formToken;
}
是否有任何实现实际显示如何在 ASP.NET5
中检索这些令牌在控制器生成
using Microsoft.AspNet.Mvc;
using Microsoft.Framework.DependencyInjection;
namespace MyApp.App.Controllers
{
public class MyController : Controller
{
public string GetAntiForgeryTokens()
{
var antiForgery = Context.RequestServices.GetService<AntiForgery>();
AntiForgeryTokenSet antiForgeryTokenSet = antiForgery.GetTokens(Context, null);
string output = antiForgeryTokenSet.CookieToken + ":" + antiForgeryTokenSet.FormToken;
return output;
}
}
}
在查看时生成
@inject AntiForgery antiForgery
@functions
{
public string GetAntiForgeryTokens()
{
AntiForgeryTokenSet antiForgeryTokenSet = antiForgery.GetTokens(Context, null);
string output = antiForgeryTokenSet.CookieToken + ":" + antiForgeryTokenSet.FormToken;
return output;
}
}
<body>
@GetAntiXsrfToken()
</body>
验证
var antiForgery = Context.RequestServices.GetService<AntiForgery>();
antiForgery.Validate(Context, new AntiForgeryTokenSet(formToken, cookieToken));
使用 MVC 实现此目的的另一种方法是使用 HTML 帮助程序在创建 cookie 和隐藏输入字段令牌的视图上获取令牌。
<form>
@Html.AntiForgeryToken()
</form>
HTML 输出:
<input name="__RequestVerificationToken" type="hidden" value="*** />
现在表单令牌已经存在,我们可以在 header 中发送令牌或将其添加到 API 期望的模型中。 API 可以使用处理自定义防伪令牌验证的 ActionFilter 进行保护。类似于 [Authorize] 的工作方式
[ValidateAntiForgeryToken]
public class MyController : ApiController
逻辑是读取 headers,其中可以找到 cookie 和 header 值标记。然后可以使用对
的调用对其进行评估AntiForgery.Validate(cookieToken, headerToken);
然后过滤器可以接受或拒绝请求。
拒绝返回:
HttpStatusCode.Forbidden
现在有 sample in the source code。该示例使用 Angular 1.x。在该示例的基础上,通过使用 Filter 进行验证,这是一个粗略的示例。在 Startup
需要设置令牌:
public void Configure(IApplicationBuilder app, IAntiforgery antiforgery)
{
app.Use(next => context =>
{
if (!context.Request.Path.Value.StartsWith("/api/"))
{
// We can send the request token as a JavaScript-readable cookie, and Angular will use it by default.
var tokens = antiforgery.GetAndStoreTokens(context);
context.Response.Cookies.Append("XSRF-TOKEN", tokens.RequestToken, new CookieOptions() { HttpOnly = false });
}
return next(context);
});
…
}
然后可以使用过滤器来验证令牌:
public class AntiforgeryValidationFilter : IAsyncActionFilter
{
private readonly IAntiforgery antiforgery;
public AntiforgeryValidationFilter(IAntiforgery antiforgery)
{
this.antiforgery = antiforgery;
}
public async Task OnActionExecutionAsync(ActionExecutingContext context, ActionExecutionDelegate next)
{
if (context.HttpContext.Request.Path.Value.StartsWith("/api/"))
{
await antiforgery.ValidateRequestAsync(context.HttpContext);
}
await next();
}
}
然后在Startup
中注册过滤器:
public void ConfigureServices(IServiceCollection services)
{
// Angular's default header name for sending the XSRF token.
services.AddAntiforgery(options => options.HeaderName = "X-XSRF-TOKEN");
services
.AddMvc(options =>
options.Filters.Add(typeof(AntiforgeryValidationFilter)))
…
}