Access-Control-Allow-Origin错误,但请求通过 [英] Access-Control-Allow-Origin error but request goes through

查看:603
本文介绍了Access-Control-Allow-Origin错误,但请求通过的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我目前正在部署一个基本的API到我的活动服务器,我正在(我认为是)一个CORS问题,但有一些行为,我不能解释。

I'm currently deploying a basic API to my live server and I'm running into (what I think is) a CORS problem but there is some behavior going on that I can't explain.

我正在从一个AngularJS前端通讯到一个Laravel 5(+ laravel-cors )后端。

I'm communicating from an AngularJS front-end to a Laravel 5 (+ laravel-cors) back-end.

我开始测试一个简单的jQuery AJAX调用(下面),当我从我的本地Vagrant环境( http:// dev .example.local / test.html )至 http://api.example.com/v1/matches 我收到一个关于 Access-Control-Allow-Origin 。奇怪的是,请求的确是因为信息是通过基于Laravel的API正确存储在数据库中的。

I started testing with a simple jQuery AJAX call (below) and when I make a request from my local Vagrant environment (http://dev.example.local/test.html) to http://api.example.com/v1/matches I get an error about Access-Control-Allow-Origin. The weird thing is that the request does come through because the information is stored in the database via the Laravel-based API correctly.

$.ajax({
    method: 'POST',
    url: 'http://api.example.com/v1/players',
    data: {
        "username": "username",
        "first_name": "First",
        "last_name": "Last",
        "nickname": ""
    }
}).always(function(r) {
    console.log(r);
});

错误:

XMLHttpRequest cannot load http://api.example.com/v1/players. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://other.example.com' is therefore not allowed access.

console.log(r) {readyState:0,responseJSON:undefined,status:0,statusText:error}

应用程序本地使用Homestead VM(API)和Vagrant环境(应用程序),并且在这些环境中正常工作...

I developed the application locally using a Homestead VM (API) and a Vagrant environment (application) and it's working correctly within these environments...

一些意见:


  • 每个请求都显示方法: POST ,状态: 200 OK

  • 正如Postman和PhpStorm的RESTful服务测试工具一样,工具类似,类型: xhr

  • Each of these requests shows up with Method: POST, Status: 200 OK, Type: xhr in my Chrome Developer Tools.
  • Tools like Postman and PhpStorm's RESTful service tester correctly execute the request and the data is added without errors.

有关如何进一步调试此问题的任何建议都是欢迎的...我'

Any ideas on how to further debug this problem are welcome... I've been trying to wrap my head around this for the entire day now and I just don't know what's causing it.

推荐答案

当Postman或PhpStorm的RESTful服务测试程序发送请求时,您没有看到任何类似问题的原因是因为这些服务不会向请求发送 Origin 标头,因为它们不受同源策略的限制。默认情况下,浏览器会将此标头附加到任何跨源的ajax请求,因为浏览器受到同源策略的限制。在我的前一个场景中,请求头将如下所示: Origin:http://stackoverflow.com 。实施 CORS规范的浏览器需要添加此请求标头,以便服务器能够确定如果请求的来源已被列入跨源头ajax请求的白名单。如果是这种情况,服务器将返回正确的 Access-Control-Allow-Origin 头。如果不是,它可以简单地省略头。没有实现CORS规范的浏览器将拒绝发送这样的ajax请求。

The reason you are not seeing any similar issues when the request is sent by Postman or PhpStorm's RESTful service tester is due to the fact that these services do not send an Origin header with the request, as they are not subject to the Same Origin policy. By default, the browser will append this header to any cross-origin ajax requests, as browsers are subject to the Same Origin Policy. In my previous scenario, the request header would look like this: Origin: http://stackoverflow.com. Browsers that implement the CORS spec are required to add this request header so the server is able to determine if the origin of the request has been whitelisted for cross-origin ajax requests. If this is the case, the server will return the proper Access-Control-Allow-Origin header. If not, it can simply omit the header. Browsers that do not implement the CORS spec will simply refuse to send such an ajax request.

关于为什么请求被发送的第一个地方,归结为简单和非简单CORS请求之间的区别。对于简单的CORS请求,请求将始终发送到服务器,但是客户端/ JS将无法解析响应,没有来自服务器的正确确认。一些CORS请求不是简单的,可以这么说。这些是例如 DELETE PATCH 请求,或 POST Content-Type of的C> / GET application / json,而不是multipart / form-data)。换句话说,如果不能使用JavaScript不能发送请求,则请求不是简单的。例如,< form> 提交或来自< script src =...> 将总是发送简单请求。对于非简单请求,浏览器必须预检请求。这意味着浏览器会在原始请求之前发送一个中间请求(称为预检)。 此预检请求是一个 OPTIONS 请求。服务器必须在对此预检的响应中返回头,以确认原始请求的任何非标准属性。如果是,则浏览器将发送原始请求。

Regarding your bewilderment as to why the request is being sent in the first place, that comes down to a distinction between "simple" and "non-simple" CORS requests. For simple CORS requests, the request will always be sent to the server, but the client/JS will not be able to parse the response without proper acknowledgement from the server. Some CORS requests are not simple, so to speak. These are, for example, DELETE or PATCH requests, or POST/GET requests that contain non-standard headers (such as X-headers or a Content-Type of "application/json" as opposed to "multipart/form-data"). In other words, a request is not simple if it cannot be sent without JavaScript. For example, a <form> submit, or a GET request from a <script src="..."> will always send "simple" requests. For non-simple requests, the browser must "preflight" the request. This means that the browser sends an intermediate request, called a preflight, before the original request. This preflight request is an OPTIONS request. The server must than return headers in the response to this preflight that acknowledge any non-standard properties of the original request. If it does, then the browser will send the original request.

您可以在 MDN

这篇关于Access-Control-Allow-Origin错误,但请求通过的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆