XDomainRequest object for cross-origin AJAX request in a browser that doesn’t support CORS
Because CORS protocol doesn’t work under IE10, XMLHttpRequest can’t be used for cross-origin AJAX requests in browsers below IE10. I wrote this article to share my experience with cross-origin AJAX request considering IE9 compatibility.
Three workarounds to solve the same-origin policy in the browser.
- CORS : Cross-Origin Resource Sharing is a mechanism that uses additional HTTP headers to tell browsers to give a web application running at one origin, access to selected resources from a different origin.
- Proxy server : A server application that acts as an intermediary for requests from clients seeking resources from the target server that provide those resources.
- JSONP : Enable fetching data, Bypassing same-origin policy by loading a <script> tag.
The first method, CORS, is the ideal solution. But it doesn’t work in IE9. And the second method, proxy, was not suitable for me because the project is used in web servers of many domains. So JSONP is the only way to bypass the same-origin policy in IE9. But I found another way. That is the XDomainRequest.
4. XDomainRequest : It was made for cross-origin requests in Internet Explorer 8 and 9.
Although I found this, I recommend JSONP than XDR. Because XDR has some limitations.
What are the limitations of XDR?
The restrictions are explained in detail in the article at the link above. The summary is as follows.
- The target URL must be accessed using the HTTP or HTTPS protocols
: No problem - The target URL must be accessed using only the HTTP methods GET and POST
: No problem - No custom headers may be added to the request
: This can be a problem. - Only text/plain is supported for the request’s Content-Type header
: This can be a problem. - No authentication or cookies will be sent with the request
: This is a critical limitation for my service using cookie-session authentication - Requests targeted to Intranet URLs may only be made from the Intranet Zone.
: This can be a problem. - Requests must be targeted to the same scheme as the hosting page.
: No problem
Even with the above restrictions, we choose XDR instead of JSONP. We decide to support IE9 partially. In IE9, personalized data was not exposed, and a pop-up recommending using IE11 or higher is displayed. The code below makes a polyfill for window.fetch by using XDR in browsers that don’t support CORS.
A. Use Feature detection instead of user-agent
This article(https://developer.mozilla.org/en-US/docs/Web/HTTP/Browser_detection_using_the_user_agent) claims to use feature detection for browser detection, not user agent.
I tried to detect if the target browser has CORS function. Both IE9 and IE10 have XDomainRequest in window object. To pick only browsers that don’t support CORS function, I add the condition that XHR instance don’t have ‘withCredentials’ property to the intersection condition.
if (window.XDomainRequest && !('withCredentials' in new XMLHttpRequest())) { window.fetch = fetchWithXDomainRequest;}
B. Wrap XDomainRequest with Promise interface.
The Fetch API returns a promise instance. To use XDR with Fetch API, we need to wrap the XDR with Promise protocol.
C. The XDomainRequest error handler does not provide any information about the error.
If the response status code is 4xx or 5xx, the error handler operates, but no information is provided as an argument. So you can only detect that an error has occurred.
xdr.onerror = function() { reject();};
Again, I recommend JSONP over XDR if you want to use a cross-origin request in a browser that doesn’t provide CORS. But if you still want to use XDR, I hope my experience will be helpful.
Thanks for reading this article.