Spring MVC 预授权控制器操作未获得 POST 请求
Spring MVC preauthorize Controller action not getting POST request
Spring MVC 和 Ajax 方面的菜鸟。我正在尝试使用 jQuery Ajax post 将一些数据从视图发送到控制器,但它要么给我 405 handleHttpRequestMethodNotSupported
要么 403 :-( 有人可以指出我的方向正确吗?
这是我的控制器操作 preAuthorize
。
@PreAuthorize( "hasAuthority('Admin')" )
@RequestMapping( value = "/configSave", method = RequestMethod.POST )
public String saveConfiguration( @RequestParam String test )
{
return "configSave";
}
以下是发送 post 请求的页面中的代码。
...
<input type="button" value="Save" id="save" onclick="saveConfig()"/>
...
function saveConfig()
{
var testPost = { test: "testing"};
$.ajax(
{
url: "hello/configSave",
data: "{'test':'testing'}",
contentType: "application/x-www-form-urlencoded",
type: "post",
beforeSend: function (xhr) {
xhr.setRequestHeader("Accept", "application/json");
xhr.setRequestHeader("Content-Type", "application/json");
},
success: function () {
alert("foo");
},
error: function() {
alert("bar");
}
}
);
}
它所做的只是抛出一个 403(目前为 405)错误并带有 bar
警报。
编辑:
令人惊讶的是,当我不执行 ajax post(我需要执行)时,它会调用控制器中的 configSave
操作。只是对这种行为感到非常困惑!
添加headers = "Accept=application/json"
将contentType: "application/x-www-form-urlencoded",
替换为contentType : "application/json",
这里有很多活动部件。你为什么不把它分解并在更小的部分进行验证。在 Spring authentication
之外创建类似的代码。一旦 Ajax
正常工作,您就可以添加 Spring authentication
回来。 403
与 405
无关。因为,这只是 header mis-match 而其他是安全问题。
设法在 Spring 文档 this and this 中找到几个部分,其中说我需要使用 CSRF 令牌发送 post 请求,当使用 Spring 安全。经过大量测试和跟踪,我发现以下代码对我有用。我希望它也能帮助其他人。欢迎大家提出更好的建议。
...<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>...
...<sec:csrfMetaTags />...//Within <head>
...var csrfToken = $("meta[name='_csrf']").attr("content");...//somewhere in page load
function saveConfig()
{
var test = { name: "testing" };
$.ajax(
{
url: "hello/configSave",
data: JSON.stringify( test ),
dataType: "text",
contentType: "application/json",
type: "post",
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json',
'X-CSRF-TOKEN': csrfToken //adding this made it WORK!
},
success: function (msg) {
alert("Yippie! Saved");
},
error: function() {
alert("Save failed, please try again!");
}
}
);
}
Spring MVC 和 Ajax 方面的菜鸟。我正在尝试使用 jQuery Ajax post 将一些数据从视图发送到控制器,但它要么给我 405 handleHttpRequestMethodNotSupported
要么 403 :-( 有人可以指出我的方向正确吗?
这是我的控制器操作 preAuthorize
。
@PreAuthorize( "hasAuthority('Admin')" )
@RequestMapping( value = "/configSave", method = RequestMethod.POST )
public String saveConfiguration( @RequestParam String test )
{
return "configSave";
}
以下是发送 post 请求的页面中的代码。
...
<input type="button" value="Save" id="save" onclick="saveConfig()"/>
...
function saveConfig()
{
var testPost = { test: "testing"};
$.ajax(
{
url: "hello/configSave",
data: "{'test':'testing'}",
contentType: "application/x-www-form-urlencoded",
type: "post",
beforeSend: function (xhr) {
xhr.setRequestHeader("Accept", "application/json");
xhr.setRequestHeader("Content-Type", "application/json");
},
success: function () {
alert("foo");
},
error: function() {
alert("bar");
}
}
);
}
它所做的只是抛出一个 403(目前为 405)错误并带有 bar
警报。
编辑:
令人惊讶的是,当我不执行 ajax post(我需要执行)时,它会调用控制器中的 configSave
操作。只是对这种行为感到非常困惑!
添加headers = "Accept=application/json"
将contentType: "application/x-www-form-urlencoded",
替换为contentType : "application/json",
这里有很多活动部件。你为什么不把它分解并在更小的部分进行验证。在 Spring authentication
之外创建类似的代码。一旦 Ajax
正常工作,您就可以添加 Spring authentication
回来。 403
与 405
无关。因为,这只是 header mis-match 而其他是安全问题。
设法在 Spring 文档 this and this 中找到几个部分,其中说我需要使用 CSRF 令牌发送 post 请求,当使用 Spring 安全。经过大量测试和跟踪,我发现以下代码对我有用。我希望它也能帮助其他人。欢迎大家提出更好的建议。
...<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>...
...<sec:csrfMetaTags />...//Within <head>
...var csrfToken = $("meta[name='_csrf']").attr("content");...//somewhere in page load
function saveConfig()
{
var test = { name: "testing" };
$.ajax(
{
url: "hello/configSave",
data: JSON.stringify( test ),
dataType: "text",
contentType: "application/json",
type: "post",
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json',
'X-CSRF-TOKEN': csrfToken //adding this made it WORK!
},
success: function (msg) {
alert("Yippie! Saved");
},
error: function() {
alert("Save failed, please try again!");
}
}
);
}