为什么重定向的CORS请求失败?

时间:2021-01-24 15:39:02

My problem is with a angularjs $http call on my app running at localhost:8080

我的问题是在我的应用程序运行localhost:8080上的angularjs $ http调用

var url "https://api.acme.com/RX/v1/user";
$http.get(url).success(function (data) {
    alert('yay');
$scope.user = data;
});

The first request succeeds with the following response recorded by Chrome:

第一个请求成功,Chrome记录了以下响应:

Status Code:302 Found
Access-Control-Allow-Credentials:true
Access-Control-Allow-Origin:http://localhost:8080
Location:https://login.acme.com/cas/login?service=https%3A%2F%2Fapi.acme.com%2FRX%2Fv1%2Fuser

This results in the browser making a second GET request to the redirect location:

这导致浏览器向重定向位置发出第二个GET请求:

https://login.acme.com/cas/login?service=https%3A%2F%2Fapi.acme.com%2FRX%2Fv1%2Fuser

This second request fails with the following error reported in Chrome:

第二个请求失败,Chrome中报告了以下错误:

XMLHttpRequest cannot load https://login.acme.com/cas/login?service=https%3A%2F%2Fapi.acme.com%2FRX%2Fv1%2Fuser. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.

So I have a CORS request from an origin to a url that allows the request that is being redirected to another url that is also configured to allow the request. But the redirect request is failing. Should I expect this to work?

所以我有一个从源到URL的CORS请求,允许将请求重定向到另一个也配置为允许请求的URL。但是重定向请求失败了。我应该期待这个吗?

Note, both api.acme.com and login.acme.com are configured to allow all origins using

请注意,api.acme.com和login.acme.com都配置为允许使用所有来源

Access-Control-Allow-Origin: *

3 个解决方案

#1


2  

see step 6 of this section(7.1.7): http://www.w3.org/TR/cors/#redirect-steps

见本节(7.1.7)的第6步:http://www.w3.org/TR/cors/#redirect-steps

more discussion could be found here: https://code.google.com/p/chromium/issues/detail?id=154967

可以在此处找到更多讨论:https://code.google.com/p/chromium/issues/detail?id = 154967

Unfortunately the convention of transmitting the string "null" makes it seem like it could be a bug; I thought so myself until I tracked this down :)

不幸的是,传输字符串“null”的惯例使它看起来像是一个bug;我自己这么想,直到我追踪到这个:)

#2


2  

The problem was caused by the browser setting the Origin to null when the 302 comes back from the XHR request. As an aside this seems strange to me as surely it would make more sense to make the 302 with the original Origin, not null.

问题是由于当302从XHR请求返回时,浏览器将Origin设置为null。顺便说一句,这对我来说似乎很奇怪,因为使用原始Origin制作302更有意义,而不是null。

When the Origin null arrived at our server, the apache tomcat CORS implementation there (http://tomcat.apache.org/tomcat-7.0-doc/config/filter.html#CORS_Filter, tomcat 7.0.52) does not return an Access-Control-Allow-Origin header, even if the server is configured to allow ALL origins. NB: This behaviour is now fixed in the current version of Tomcat 7.

当Origin null到达我们的服务器时,那里的apache tomcat CORS实现(http://tomcat.apache.org/tomcat-7.0-doc/config/filter.html#CORS_Filter,tomcat 7.0.52)不返回Access -Control-Allow-Origin标头,即使服务器配置为允许所有来源。注意:此行为现已在当前版本的Tomcat 7中得到修复。

The solution was to use a different CORS implementation on the server (http://software.dzhuvinov.com/cors-filter.html). This filter returns Access-Control-Allow-Origin: null and the 302 XHR succeeds.

解决方案是在服务器上使用不同的CORS实现(http://software.dzhuvinov.com/cors-filter.html)。此过滤器返回Access-Control-Allow-Origin:null并且302 XHR成功。

Although I have found a solution I am still uncertain of two things:

虽然我找到了解决方案,但我仍然不确定两件事:

  1. why the browser sends Origin null when an XHR results in a redirect
  2. 当XHR导致重定向时,浏览器为什么发送Origin null

  3. whether the tomcat filter or the dzhuvinov software filter is responding correctly to Origin null.
  4. tomcat过滤器或dzhuvinov软件过滤器是否正确响应Origin null。

#3


0  

if you use LoginRequiredMiddleware, be sure to add the url to LOGIN_EXEMPT_URLS in settings.py.

如果您使用LoginRequiredMiddleware,请务必在settings.py中将URL添加到LOGIN_EXEMPT_URLS。

#1


2  

see step 6 of this section(7.1.7): http://www.w3.org/TR/cors/#redirect-steps

见本节(7.1.7)的第6步:http://www.w3.org/TR/cors/#redirect-steps

more discussion could be found here: https://code.google.com/p/chromium/issues/detail?id=154967

可以在此处找到更多讨论:https://code.google.com/p/chromium/issues/detail?id = 154967

Unfortunately the convention of transmitting the string "null" makes it seem like it could be a bug; I thought so myself until I tracked this down :)

不幸的是,传输字符串“null”的惯例使它看起来像是一个bug;我自己这么想,直到我追踪到这个:)

#2


2  

The problem was caused by the browser setting the Origin to null when the 302 comes back from the XHR request. As an aside this seems strange to me as surely it would make more sense to make the 302 with the original Origin, not null.

问题是由于当302从XHR请求返回时,浏览器将Origin设置为null。顺便说一句,这对我来说似乎很奇怪,因为使用原始Origin制作302更有意义,而不是null。

When the Origin null arrived at our server, the apache tomcat CORS implementation there (http://tomcat.apache.org/tomcat-7.0-doc/config/filter.html#CORS_Filter, tomcat 7.0.52) does not return an Access-Control-Allow-Origin header, even if the server is configured to allow ALL origins. NB: This behaviour is now fixed in the current version of Tomcat 7.

当Origin null到达我们的服务器时,那里的apache tomcat CORS实现(http://tomcat.apache.org/tomcat-7.0-doc/config/filter.html#CORS_Filter,tomcat 7.0.52)不返回Access -Control-Allow-Origin标头,即使服务器配置为允许所有来源。注意:此行为现已在当前版本的Tomcat 7中得到修复。

The solution was to use a different CORS implementation on the server (http://software.dzhuvinov.com/cors-filter.html). This filter returns Access-Control-Allow-Origin: null and the 302 XHR succeeds.

解决方案是在服务器上使用不同的CORS实现(http://software.dzhuvinov.com/cors-filter.html)。此过滤器返回Access-Control-Allow-Origin:null并且302 XHR成功。

Although I have found a solution I am still uncertain of two things:

虽然我找到了解决方案,但我仍然不确定两件事:

  1. why the browser sends Origin null when an XHR results in a redirect
  2. 当XHR导致重定向时,浏览器为什么发送Origin null

  3. whether the tomcat filter or the dzhuvinov software filter is responding correctly to Origin null.
  4. tomcat过滤器或dzhuvinov软件过滤器是否正确响应Origin null。

#3


0  

if you use LoginRequiredMiddleware, be sure to add the url to LOGIN_EXEMPT_URLS in settings.py.

如果您使用LoginRequiredMiddleware,请务必在settings.py中将URL添加到LOGIN_EXEMPT_URLS。