用户注册中出现了所需的防伪表单字段“__RequestVerificationToken”不存在的错误。

163
我正在使用Membership.create用户函数,但出现以下错误,

所需的防伪造表单字段“__RequestVerificationToken”不存在

我该如何解决?
22个回答

248
您的操作之前应该添加[ValidateAntiForgeryToken]属性。您还应该在表单中添加@Html.AntiForgeryToken()

15
我有一个网页,它存在同样的问题,但整体看起来是正确的。问题出在哪里? - ConductedClever
@ConductedClever 你应该仔细检查所有内容(字段,cookie),使用Fiddler和/或Firebug(任何浏览器开发工具)进行检查,参考这篇文章:http://www.asp.net/web-api/overview/security/preventing-cross-site-request-forgery-%28csrf%29-attacks - webdeveloper
我在测试中一切正常,客户机器上也一直运行良好,但最近出现了这个错误。我不知道为什么会这样。请问有没有其他想法?除了列在这里的那些。 - Andrei Dobrin
为什么会发生这种事?他们又发明了什么东西? - Antoine Pelletier
1
Html.AntiForgeryToken(); 不起作用!!改成 @Html.AntiForgeryToken() 就可以了。 - FindOutIslamNow
显示剩余2条评论

91
在我的情况下,我在我的web.config中有这个配置: 但我的项目未设置使用SSL。将该行注释或设置项目始终使用SSL即可解决该问题。

3
在我的情况下,web.config 文件中有 requireSSL,但是 IIS 绑定了 80 端口和 443 端口。因此,输入 https 的用户得到了正确的行为,而输入 http 的用户则会出现错误。加入一个重写规则强制所有请求都使用 https://{HTTP_HOST}/{R:1} 可以解决这个问题。 - user1069816
谢谢。在我的情况下,在IIS中有这个绑定(https»EmptyHostName»IP»443),但没有一个绑定(https»www.mysite.com»IP»443)。因此,我添加了一个新的绑定,其中https非空主机名等于该域,并解决了问题。我在IIS中设置了重写设置,以强制使用http 2 https - Ramin Bateni

70

就像这样:

控制器

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult MethodName(FormCollection formCollection)
{
     ...
     Code Block
     ...
}

视图:

@using(Html.BeginForm())
{
     @Html.AntiForgeryToken()
     <input name="..." type="text" />
     // rest
}

尝试仅在HTML中使用。 - Subrata Sarkar

43
同时确保在[HttpGet]下避免不使用[ValidateAntiForgeryToken]。
  [HttpGet]
  public ActionResult MethodName()
  {
  ..
  }

1
这个回答补充了其他答案并解决了我的问题!谢谢 - Lucas
2
此答案假定您没有保存任何提交的数据(在 HttpGet 上不应该这样做)。如果您正在保存数据,则仍需要 [ValidateAntiForgeryToken] 提供的 XSRF 保护。 - thelem

13

即使未启用Cookies,您仍将收到该错误。


2
好的,我遇到了同样的问题。我之前使用的是Internet Explorer浏览器,但是改用Chrome浏览器后问题得到了解决。 - FindOutIslamNow
这也解决了我的问题。在谷歌浏览器中启用cookies。谢谢。 - The Scientific Method

11
另一个可能导致此问题的原因(我刚遇到了这个问题)是以下情况: 如果某种原因禁用了表单中的所有输入字段。 它将禁用持有验证令牌的隐藏输入字段。 当表单被提交时,令牌值将丢失并生成缺少错误。所以你需要重新启用持有验证令牌的输入字段,就可以解决问题了。

那是我的问题和解决方案。谢谢,发现得真好! - East of Nowhere

10

在我的情况下,是由于在webconfig中添加requireSSL=truehttpcookies导致AntiForgeryToken停止工作。例如:

<system.web>
  <httpCookies httpOnlyCookies="true" requireSSL="true"/>
</system.web>

为了让requireSSL=true@Html.AntiForgeryToken()都能起作用,我在Global.asaxApplication_BeginRequest中添加了这行代码。
    protected void Application_BeginRequest(object sender, EventArgs e)
  {
    AntiForgeryConfig.RequireSsl = HttpContext.Current.Request.IsSecureConnection;
  }

8
另一种可能性是,如果我们作为请求的一部分上传文件,而内容长度超过了<httpRuntime maxRequestLength="以千字节为单位的大小" />,并且您正在使用请求验证令牌,则浏览器会显示'所需的防伪表单字段“__RequestVerificationToken”不存在'消息,而不是请求长度超过消息。
将maxRequestLength设置为足够大的值来满足请求可以解决即时问题-尽管我承认这不是一个正确的解决方案(我们希望用户知道文件大小的真正问题,而不是缺少请求验证令牌的问题)。

7
在我的情况下,我在表单提交时使用了这个JavaScript代码:
$('form').submit(function () {
    $('input').prop('disabled', true);
});

这是从提交的表单中移除了隐藏的RequestVerificationToken。我将其更改为:
$('form').submit(function () {
    $('input[type=submit]').prop('disabled', true);
    $('input[type=text]').prop('readonly', true);
    $('input[type=password]').prop('readonly', true);
});

...然后它运行得很好。


当您禁用输入时,您是如何注意到反键受到影响的? - Cer
1
@Cer - 如果你想知道我是怎么发现的,我用 Fiddler 检查了请求,并发现密钥没有被发送。然后我读到 Html 提交不会包括禁用的控件。所以我把它改成了 readonly 并排除了隐藏的控件。看起来效果很好。 - Sean

6

在您的控制器中,请确保您拥有您的http属性,例如:

[HttpPost]

同时在控制器中添加该属性:
[ValidateAntiForgeryToken]

在您的视图表单中,您需要编写以下内容:
@Html.AntiForgeryToken();

我在代码块中使用了Html.AntiForgeryToken(),但没有加上@符号,在Razor中并没有出现错误,但在运行时却出错了。 确保你注意到@Html.Ant..中的@符号是否存在


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接