Ajax json跨域发布到控制器,“不允许”访问控制允许标头
我创建了一个简单的 MVC 控制器操作,它接受一些 json 数据 - 然后返回 true 或 false。
[AllowCrossSiteJson]
public JsonResult AddPerson(Person person)
{
//do stuff with person object
return Json(true);
}
我从 javascript 调用它:
function saveData(person) {
var json = $.toJSON(person); //converts person object to json
$.ajax({
url: "http://somedomain.com/Ajax/AddPerson",
type: 'POST',
dataType: 'json',
data: json,
contentType: 'application/json; charset=utf-8',
success: function (data) {
alert("ok");
}
});
}
只要我在同一个域中,一切都会正常,但是一旦我从另一个域调用它,我就会遇到问题。
控制器上有一个操作过滤器“AllowCrossSiteJson”,它将标头“Access-Control-Allow-Origin”设置为“*”,允许任何源访问控制器操作。
public class AllowCrossSiteJsonAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
filterContext.RequestContext.HttpContext.Response.AddHeader("Access-Control-Allow-Origin", "*");
base.OnActionExecuting(filterContext);
}
}
但是 - 当跨域调用时,我在 firebug 中收到此错误:
选项http://somedomain.com/Ajax/AddPerson?packageId=3 500(内部服务器错误) XMLHttpRequest 无法加载 http://somedomain.com/Ajax/AddPerson。 Access-Control-Allow-Headers 不允许请求标头字段 Content-Type。
这里出了什么问题?
我几个小时以来一直在寻找可能的解决方案,这似乎与使用 OPTIONS 的 jquery 有关(而不是我期望的 POST)。
如果这确实是问题,我该如何解决?
I create a simple MVC Controller action, that takes some json data - then return true or false.
[AllowCrossSiteJson]
public JsonResult AddPerson(Person person)
{
//do stuff with person object
return Json(true);
}
I call it from javascript:
function saveData(person) {
var json = $.toJSON(person); //converts person object to json
$.ajax({
url: "http://somedomain.com/Ajax/AddPerson",
type: 'POST',
dataType: 'json',
data: json,
contentType: 'application/json; charset=utf-8',
success: function (data) {
alert("ok");
}
});
}
Everything works as long as I am on the same domain, but as soon as I call it from another domain, I run into problems.
On the controller is an action filter "AllowCrossSiteJson" that sets the header "Access-Control-Allow-Origin" to "*", allowing any origin to access the controller action.
public class AllowCrossSiteJsonAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
filterContext.RequestContext.HttpContext.Response.AddHeader("Access-Control-Allow-Origin", "*");
base.OnActionExecuting(filterContext);
}
}
However - I then get this error in firebug, when calling across domains:
OPTIONS http://somedomain.com/Ajax/AddPerson?packageId=3 500 (Internal Server Error)
XMLHttpRequest cannot load http://somedomain.com/Ajax/AddPerson. Request header field Content-Type is not allowed by Access-Control-Allow-Headers.
What is wrong here?
I have been looking through possible solutions for hours, and it seems to be something to do with jquery using OPTIONS (not POST as I would expect).
If that is indeed the problem, how can I fix that?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
要修复 Access-Control-Allow-Origin 错误,您需要在响应中包含以下标头:
Access-Control-Allow-Headers: Content-Type
基本上,任何“非简单”标头需要以逗号分隔的列表形式包含在上面的标题中。查看 CORS 规范以了解更多详细信息:
http://www.w3.org/TR/cors/
“内容-Type”需要包含在内,因为“application/json”与此处定义的值不匹配:
http://www. w3.org/TR/cors/#terminology
To fix the Access-Control-Allow-Origin error, you need to include the following header in your response:
Access-Control-Allow-Headers: Content-Type
Basically, any "non-simple" header needs to be included as a comma-delimited list in the header above. Check out the CORS spec for more details:
http://www.w3.org/TR/cors/
"Content-Type" needs to be included because "application/json" does not match the values defined here:
http://www.w3.org/TR/cors/#terminology
我推荐您 JSONP,它是唯一真正跨浏览器且可靠的跨域 AJAX 解决方案。因此,您可以首先编写一个自定义操作结果,该结果将用回调包装 JSON 响应:
然后:
最后执行跨域 AJAX 调用:
I'd recommend you JSONP, it's the only really cross browser and reliable solution for cross domain AJAX. So you could start by writing a custom action result that will wrap the JSON response with a callback:
and then:
and finally perform the cross domain AJAX call: