如何在MVC中使用AJAX POST请求携带AntiForgeryToken,以及解决删除按钮需保留防伪令牌才能调用控制器方法的问题
这是因为你的AJAX请求没携带.NET要求的防伪令牌,所以[ValidateAntiForgeryToken]特性直接拦截了请求——这正是它的作用,防止CSRF攻击,所以咱们得让AJAX把令牌一起发过去,下面是两种靠谱的解决方法:
方法1:手动在AJAX请求中携带令牌
首先确保你的视图页面里已经生成了防伪令牌的隐藏字段(Razor视图默认会有,要是没有就手动加一行@Html.AntiForgeryToken()),它会生成类似这样的HTML:
<input name="__RequestVerificationToken" type="hidden" value="加密的令牌值" />
然后修改你的AJAX代码,把这个令牌值加到请求里就行,两种方式任选:
方式A:把令牌放在请求数据里
$("table").on("click", ".btn-delete", function (e) { var thisId = $(this).data('id'); // 拿到页面里的防伪令牌 var token = $('input[name="__RequestVerificationToken"]').val(); if (confirm("Are you sure you want to delete this item?")) { $.post('/AdminPortal/Client/Delete/', { id: thisId, __RequestVerificationToken: token // 把令牌和ID一起发送 }, function (data) { window.location.href = "/AdminPortal/Client/Index"; }); } });
方式B:把令牌放在请求头中
这种方式更干净,尤其适合多个AJAX请求的场景:
$("table").on("click", ".btn-delete", function (e) { var thisId = $(this).data('id'); var token = $('input[name="__RequestVerificationToken"]').val(); if (confirm("Are you sure you want to delete this item?")) { $.ajax({ url: '/AdminPortal/Client/Delete/', type: 'POST', headers: { // 把令牌放在请求头里 'RequestVerificationToken': token }, data: { id: thisId }, success: function(data) { window.location.href = "/AdminPortal/Client/Index"; } }); } });
方法2:全局配置jQuery自动携带令牌
如果你的页面有很多AJAX POST请求,可以一次性配置jQuery,让它自动给所有POST请求带上令牌,省得每个请求都手动加:
在页面的脚本初始化部分加这段代码:
$(document).ready(function() { // 拿到页面的防伪令牌 var token = $('input[name="__RequestVerificationToken"]').val(); // 全局设置AJAX请求头 $.ajaxSetup({ headers: { 'RequestVerificationToken': token } }); });
这样你的原AJAX代码完全不用改,所有POST请求都会自动带上令牌,控制器的[ValidateAntiForgeryToken]特性就能正常验证了。
注意事项
你的控制器代码不需要做任何修改——保留[HttpPost]和[ValidateAntiForgeryToken]是最安全的做法,这正是.NET防止跨站请求伪造的核心机制,千万不要去掉它。
内容的提问来源于stack exchange,提问作者RobertDev22
相关产品推荐
相关产品推荐

