Understanding Xmlhttprequest Over Cors (Responsetext)

Understanding XMLHttpRequest over CORS (responseText)

For a "simple" HTTP verb like GET or POST, yes, the entire page is fetched, and then the browser decides whether JavaScript gets to use the contents or not. The server doesn't need to know where the requests comes from; it is the browser's job to inspect the reply from the server and determine if JS is permitted to see the contents.

For a "non-simple" HTTP verb like PUT or DELETE, the browser issues a "preflight request" using an OPTIONS request. In that case, the browser first checks to see if the domain and the verb are supported, by checking for Access-Control-Allow-Origin and Access-Control-Allow-Methods, respectively. (See the "Handling a Not-So-Simple Request" on the CORS page of HTML5 Rocks for more information.) The preflight response also lists permissible non-simple headers, included in Access-Control-Allow-Headers.

This is because allowing a client to send a DELETE request to the server could be very bad, even if JavaScript never gets to see the cross-domain result -- again, remember that the server is generally not under any obligation to verify that the request is coming from a legitimate domain (although it may do so using the Origin header from the request).

Cannot get XmlHttpRequest to work with CORS

The http://localhost:51111 server needs to be configured to send the Access-Control-Allow-Origin response header and any other necessary Access-Control-Allow-* response headers. That’s because it’s the server to which the frontend JS code is sending the request.

The response cited in the question doesn’t show those being received as response headers, so it seems you must not have the http://localhost:51111 server configured to send them.

By default browsers won’t allow your frontend JS code to access the response from a cross-origin request—unless a server opts-in to allowing it. And the way the servers opt-in to allowing cross-origin requests is by sending the Access-Control-Allow-Origin response header in responses.

All the actual enforcement of the CORS protocol is done by browsers. So the Access-Control-Allow-Origin response header is what servers use to communicate with browsers; servers use it for telling browsers which origins they want browsers to expose responses from this server to.

So that’s why in your case the http://localhost:51111 server is the one you need to configure to send the right Access-Control-Allow-Origin response header.

CORS with IE, XMLHttpRequest and ssl (https)

I've had a similar problem that was solved by adding a dummy onprogress callback to the XDomainRequest in the IE case:

if (ieVersion > 7){ 
console.log("XDomainRequest");
xhr = new XDomainRequest();
xhr.onprogress = function() {}; // <-- add this
}

It seemed that IE was aborting the cross-domain request if there was no onprogess handler defined.


Here's a function I use for AJAX, maybe there is something in it that helps you:

  /**
* Wraps jQuery's AJAX, adds X-Domain support for IE
*
*
*/
function xDomainAJAX (url, settings) {
jQueryRequired();
$.support.cors = true; // enable x-domain
if ($.browser.msie && parseInt($.browser.version, 10) >= 8 && XDomainRequest) {
// use ms xdr
var xdr = new XDomainRequest();
xdr.open(settings.type, url + '?' + $.param(settings.data));
xdr.onprogress = function() {};
xdr.onload = function() {
settings.success(xdr.responseText);
};
xdr.onerror = settings.error;
xdr.send();
} else {
// use jQuery ajax
$.ajax(url, settings);
}
}

Native XMLHttpRequest() successfully makes CORS request but jQuery .ajax does not?

jQuery 3.0 introduced a new way of using jQuery.get that allows you to pass in a settings object. This is why the jsfiddle works on edge, but not 2.1.4, and why on your local machine it requests the local file system thus giving you a cors error. If you want to use the jQuery.get({url: theurl}) syntax, you'll have to use jQuery 3.x, otherwise you should use jQuery.get(theurl)

XMLHttpRequest gives CORS error where as $.ajax works

the jQuery ajax request you are sending is considered "simple" and therefore follows the SOP less strictly (it doesn't send an OPTIONS request.) The native javascript ajax request you are sending is not considered "simple" because you added the Content-Type header.

To fix this, you'll of course need to remove the content-type header, and then since you are no longer setting the content-type header to application/json, you'll have to format your data to be a valid paramstring. With jquery it's as simple as $.param(xyz), however, I'm assuming you're trying to do this without jQuery, so you'll need your data formatted as

config%5Bname%5D=ronak&config%5Bcountry%5D=india&token=abc

XMLHttpRequest return from a function before response is back

You are not awaiting the request. To make the existing code wait for the result, you'd need to wrap the outdated callback-based code in a promise and await that (and also I don't think getting the response text of an XHR works as you showed, I changed it now):

// This is just to demonstrate what was immediately wrong
// with the existing code - it's not the best solution! See below.

FileObject[key1][key2][key3] = await new Promise((resolve, reject) => {
var xhr = new XMLHttpRequest();
xhr.open("POST", url, true);
xhr.onreadystatechange = function() {
if (this.readyState === XMLHttpRequest.DONE && this.status === 200) {
var id = xhr.responseText;
resolve(parseInt(id));
}
};
xhr.send(formData);
});

Note there is no error handling yet, if the request fails everything will just hang.

But at that point, it doesn't actually make sense to use XHR in the first place! It's a lot more straightforward to use fetch, which has a promise API out of the box:

const response = await fetch(url, { method: 'POST', body: formData })
FileObject[key1][key2][key3] = parseInt(await response.text())


Related Topics



Leave a reply



Submit