Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to use XMLHttpRequest across Domains

Cross Site XMLHttpRequest from JavaScript can it be done?

I understand the limitations and why it is not generally able to work, but as of firefox 3.5 there is the

Access-Control-Allow-Origin: *

which is supposed to allow this to work.

It tells the browser that the server does not care if the request is sent to it from a domain that did not serve the page.

The code I am using is below.

function sendData(webservicePayload, callbackFunction) {
var request = null;
if (!window.XMLHttpRequest) { // code for IE
    try {
        request = new ActiveXObject('Msxml2.XMLHTTP');
    } catch (e) {
        try {
            request = new ActiveXObject('Microsoft.XMLHTTP');
        } catch (E) {
            return 'Create XMLHTTP request IE';
        }
    }
} else { // code for Mozilla, etc.
    request = new XMLHttpRequest();
}
/*
 * Setup the callback function
 */
request.onreadystatechange = function() {
    if (request.readyState == 4 && request.status < 300) {
        eval(callbackFunction);
    }
};
if (!request) {
    nlapiLogExecution('ERROR', 'Create XMLHTTP request', 'Failed');
    return;
}
/*
 * Setup the request headers
 */

request.open('POST','http://www.another.domain.co.uk/webservice.asmx', true);
request.setRequestHeader('Man','POST http://www.another.domain.co.uk/webservice.asmx HTTP/1.1');
request.setRequestHeader('MessageType', 'CALL');
request.setRequestHeader('Content-Type', 'text/xml; charset="utf-8"');
request.setRequestHeader('Cache-Control', 'no-cache');
request.setRequestHeader("X-Requested-With", "XMLHttpRequest");
request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');

request.setRequestHeader('SOAPAction','http://www.another.domain.co.uk/WebService/eService');
request.send(webservicePayload);

}

This is sending the correct request header

REQUEST

OPTIONS /webservice.asmx HTTP/1.1
Host: www.another.domain.co.uk
User-Agent: Mozilla/5.0 (Windows NT 6.1; rv:8.0) Gecko/20100101 Firefox/8.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-gb,en;q=0.5
Accept-Encoding: gzip, deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Connection: keep-alive
Origin: https://my.domain.com
Access-Control-Request-Method: POST
Access-Control-Request-Headers: cache-control,content-type,man,messagetype,soapaction
Pragma: no-cache
Cache-Control: no-cache

and receiving an expected response header

RESPONSE

HTTP/1.1 403 Forbidden
Server: Microsoft-IIS/5.1
Date: Wed, 14 Dec 2011 13:43:27 GMT
X-Powered-By: ASP.NET
Access-Control-Allow-Origin: *
Connection: close
Content-Type: text/html
Content-Length: 44

As you can see the Orgin is specified in the request and the server responds with acceptance of any ("*") domain.

Why am I getting "Forbidden 403" as I feel that everything I have done is correct, I can't work out why?

Is anyone else getting this?

Do you know what is causing it?

like image 692
Javanerd Avatar asked Dec 15 '11 17:12

Javanerd


1 Answers

A CORs request actually consists of two physical HTTP requests: 1) The preflight request, and 2) the actual request. The request you posted above looks like the preflight request, since it is uses the HTTP OPTIONS method. So the first thing you have to do is verify that your server accepts OPTIONS requests (I believe this should just work, but it may explain why you are receiving a 403).

Next, you need a valid preflight response. The response to a preflight request must also contain the following two headers:

Access-Control-Allow-Methods: POST
Access-Control-Allow-Headers: Origin,cache-control,content-type,man,messagetype,soapaction

(See how these response headers are an echo of the Access-Control-Request-Method and Access-Control-Request-Headers request headers). The Access-Control-Allow-Headers header should contain any custom request headers.

Once the browser receives this response, it knows that the preflight request has been accepted, and it makes the actual request. On the actual request, you only need the following header:

Access-Control-Allow-Origin: *

You can learn more about preflight requests and handling CORS requests here: http://www.html5rocks.com/en/tutorials/cors/

like image 67
monsur Avatar answered Oct 20 '22 08:10

monsur