【问题标题】:ASP.NET Core WebAPI: Validation of the provided antiforgery token failed. The cookie token and the request token were swappedASP.NET Core WebAPI:验证提供的防伪令牌失败。交换了 cookie 令牌和请求令牌
【发布时间】:2018-07-11 19:02:03
【问题描述】:

在我的 ASP.NET Core 2 WebAPI 应用程序中,我想将 AntiforgeryToken 用于我的 POST、PUT 和 DELETE 控制器方法。对于this documentation,我设置了Startup 类的ConfigureServicesConfigure 方法。在客户端,我使用 Angular 5 及其 Antiforgery 的默认配置。我不知道问题出在哪里。

这是我的 Startup.cs 的摘录

public void ConfigureServices(IServiceCollection services)
{
    // ...
    services.AddAntiforgery(options =>
    {
        options.Cookie.Name = "XSRF-TOKEN";
        options.HeaderName = "X-XSRF-TOKEN";
        options.FormFieldName = "F-XSFR-TOKEN";
    });
    // ...
}

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory, IServiceProvider provider, ILogger<Startup> logger, IAntiforgery antiforgery)
{
    // ...
    app.Use(async (context, next) =>
    {
        var tokens = antiforgery.GetAndStoreTokens(context);
        context.Response.Cookies.Append("XSRF-TOKEN", tokens.RequestToken, new CookieOptions() { HttpOnly = false });
        await next();
    });
    // ...
}

我的控制器都是这样的:

[Authorize]
[Route("api")]
public class CarController : Controller
{
    #region Variables
    private readonly DataContext _db;
    private ILogger<CarController> _logger;
    #endregion

    #region Constructor
    public CarController(DataContext db, ILogger<CarController> logger)
    {
        _db = db;
        _logger = logger;
    }
    #endregion

    #region Methods
    [AllowAnonymous]
    [HttpGet("[controller]")]
    public IActionResult Get()
    {
        try
        {
            return Ok(_db.Cars);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex.GetHashCode(), ex, ex.Message);
            return BadRequest(ex);
        }
    }

    [HttpPost("[controller]")]
    [ValidateAntiForgeryToken]
    public async Task<IActionResult> Post([FromBody] CreateCar model)
    {
        try
        {
            // Creates a new car.
        }
        catch (Exception ex)
        {
            _logger.LogError(ex.HResult, ex, ex.Message);
            return StatusCode(500, ex);
        }
    }

    [HttpPut("[controller]/{id}")]
    [ValidateAntiForgeryToken]
    public async Task<IActionResult> Put(int id, [FromBody] UpdateCar model)
    {
        try
        {
            // Updates a car
        }
        catch (Exception ex)
        {
            _logger.LogError(ex.HResult, ex, ex.Message);
            return StatusCode(500, ex);
        }
    }
    #endregion
}

【问题讨论】:

    标签: c# angular asp.net-web-api .net-core x-xsrf-token


    【解决方案1】:

    我遇到了同样的问题,我想我找到了问题。

    TLDR: options.Cookie.Name = "ASP-XSRF-TOKEN";

    AddAntiforgery中的options.Cookie.Name必须不同于您使用context.Response.Cookies.Append手动设置的cookie。

    尝试更改其中一个的名称,它会起作用。现在,您将使用 options.Cookie.Name 名称和 tokens.RequestToken 值覆盖生成的 cookie。

    您可以注意到开发者工具中的差异。

    • 使用options.Cookie.Name生成的默认令牌标记为http only (HttpOnly = true)
    • 使用context.Response.Cookies.Append 手动附加的令牌标记为HttpOnly = false

    第二个是从 JS/Angular 中读取的(您可以在 JS 中读取它,因为 HttpOnly=false 并在您的 ajax 请求中作为标头发送,并针对无法从 JS 读取的默认值进行验证)

    【讨论】:

      猜你喜欢
      • 2018-04-13
      • 2018-06-19
      • 2014-01-23
      • 2019-11-19
      • 2018-08-30
      • 2014-10-08
      • 1970-01-01
      • 2022-08-16
      • 2017-12-29
      相关资源
      最近更新 更多