Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
673 views
in Technique[技术] by (71.8m points)

jquery - Cross-domain AJAX request not working

I'm calling POST on a third-party API that I've been working with via jQuery's $.ajax function. However, when I make the call I get the following error: XMLHttpRequest cannot load http://the-url.com. The request was redirected to 'http://the-url.com/anotherlocation', which is disallowed for cross-origin requests that require preflight.

I saw from this post that this might be a Webkit bug, so I tried it in Firefox (I'm developing in Chrome) and I got the same result.I've tried this on Chrome and Firefox and I get the same result.

Per this post, I also tried using jsonp both by setting the crossDomain property of the $.ajax function to true and setting the dataType to jsonp. But, this caused a 500 internal server error.

When I start Chrome with the --disable-web-security flag, I don't have any problems. However, if I start the browser normally, then I get the error.

So, I guess this might sort of be a 2-part question. What can I do to make this cross-domain request? If JSONP is the answer, then how do I go about figuring out if the third-party API is set up correctly to support this?

EDIT: Here's the screenshot when I make the call with the browser security disabled: https://drive.google.com/file/d/0Bzo7loNBQcmjUjk5YWNWLXM2SVE/edit?usp=sharing

Here's the screenchost when I make the call with the browser security enabled (like normal): https://drive.google.com/file/d/0Bzo7loNBQcmjam5NQ3BKWUluRE0/edit?usp=sharing

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

To your first question,

What can I do to make this cross-domain request?

The following request headers are first sent to the server. Based on the response headers, the UserAgent, i.e. browser here, will discard the response(if any) and not give it back to the XHR callback, when the headers don't add up.

Origin: http://yourdomain.com Access-Control-Request-Method: POST Access-Control-Request-Headers: X-Custom-Header

Your server should then respond with the following headers:

Access-Control-Allow-Origin: http://yourdomain.com Access-Control-Allow-Methods: GET, POST, OPTIONS Access-Control-Allow-Headers: X-Custom-Header

Example taken from - https://stackoverflow.com/a/8689332/1304559

You can use tools like Fiddler or Web Inspector Network tab(Chrome) or Firebug's network tab to find the headers the server is sending back in response to your request.

The third party API server url should respond back with the supported values. If it doesn't that's your problem.

Can't be of much help in JsonP 500 server error, as it says Internal Server Error


UPDATE

I saw your screen shots, couple of things to notice here

  1. HTTP POST is used
  2. No Access-Control headers found in both modes response. With second status code as 302
  3. Origin request header is null, so I believe the HTML file is opened from the file system rather than from a web site

Enabling JSONP

Coming to the point of why JSONP is not working, reason - The web service config(of the ASMX specified), has not enabled GET mode for the request. JSONP doesn't work with POST.

Why 200 with security disabled?

The POST request is directly called with no OPTIONS or preflight request fired before it, so server simply responds back.

Why 302 status code with security enabled?

First a little on how it happens when security flag is not disabled(default). The OPTIONS request is fired to the URL. The URL should respond back with a list of HTTP methods that can be used, i.e. GET, POST, etc. The status code of this OPTIONS request should be 200.

In the current case, there is a redirect called when doing this. And the redirect is pointing to a custom error handler for a HTTP Server Error. I believe it is 404 error, which is being caught and redirected.[This could be because the custom handler is set to ResponseRedirect instead of ResponseRewrite] The reason for the 404 is cross-domain access is not enabled.

In case the custom error handling was turned off, this would have returned HTTP 500 code. I believe the problem can be found by checking the server logs immediately after firing a cross-domain request. It will be good to check the server logs for errors other than this, if any.

Possible solution

To enable access, there are two ways - detailed here. Or directly add the access control headers to web.config file's customheaders section.

When cross-domain access is enabled, the server should respond back to OPTIONS and allow the request to go through. This should return HTTP 200 unless there are other errors. But ajax callback will not be able to access the response. This can be done now only if Access-Control-Allow-Origin is set to "*" or the Origin request header value, and the Access-Control as needed. And the ajax callback will receive the response as intended.

The third point, null Origin. This will be a problem if the Origin request header value is sent back as Access-Control-Allow-Origin. But I am assuming you will be moving your HTML page to a web server, so that shouldn't be a problem.

Hope this helps!


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...