Explore several ways to request resources across domains (summary) _javascript skills

Source: Internet
Author: User
Tags event listener file upload http post script tag

Several ways to request resources across domains, as follows:

1. What is cross-domain

2.JSONP

3.proxy Agent

4.cors

5.xdr

Because the browser homology policy, usually send the request URL of the protocol, domain name, port between any one and the current page address is different from the cross domain. The following table can be viewed in detail

JSONP

This is mainly done by dynamically inserting a script tag. The browser does not have a homology restriction on the script's resource reference, and the resource is executed immediately after it is loaded into the page (without blocking).

<script>
   var _script = document.createelement (' script ');
   _script.type = "Text/javascript";
   _SCRIPT.SRC = "Http://localhost:8888/jsonp?callback=f";
   Document.head.appendChild (_script);
  </script>

In the actual project, JSONP is typically used to obtain JSON-formatted data, when the front and back ends usually contract a parameter callback, the value of which is the function name that handles the returned data.

<!doctype html>  

Disadvantages:

1, this way cannot send POST request (here)

2, in addition to determine whether the JSONP request failure is not easy, most of the implementation of the framework is the combination of timeout time to determine.

Proxy Agent

This method first sends the request to the background server, sends the request through the server, and then passes the result of the request to the front end.

<!doctype html>
 
 
var proxyurl = "";
   if (req.url.indexOf ('? ') >-1) {
     Proxyurl = req.url.substr (req.url.indexOf ('? ') + 1);
     Console.log (Proxyurl);
   }
   if (Req.method = = ' Get ') {
     request.get (proxyurl). pipe (res);
   } else if (Req.method = = ' Post ') {
     var POST = ' ;   Defines a post variable for the staging request body information

    req.on (' Data ', function (chunk) {  //) through the Req Data event listener function, which is added to the post variable whenever the requested body is received
      post = = chunk;
    });
      post = Qs.parse (post);
      Request ({method
           : ' POST ',
           url:proxyurl,
           form:post
         }). pipe (res);}
    );
   

Note that if you are acting on the HTTPS protocol request, your proxy will first need to trust the certificate (especially the custom certificate) or ignore the certificate check, or your request will not succeed. A vivid example is provided in 12306.

Also note that for the same request browser will usually read data from the cache, we sometimes do not want to read from the cache, so we will add a Preventcache parameter, this time the request URL into: url?preventcache=12345567 ...; There is no problem in itself, the problem is that when a proxy proxy request is sent using certain front-end frameworks (such as jquery), the request URL is proxy?url and the preventcache:true is set, and the framework does not handle the parameter correctly. The resulting request becomes proxy?url&preventcache=123456 (the positive length should be proxy?url?preventcache=12356), and the request sent after the back end interception is url&preventcache= 123456, there is no this address, so you do not get the correct result.

CORS

This is a way for modern browsers to support requests for cross-domain resources.

When you use XMLHttpRequest to send a request, the browser discovers that the request does not conform to the homologous policy and adds a request header to the request: Origin, a series of processing in the background, If you decide to accept the request, add a response header to the return result: Access-control-allow-origin The browser determines whether the corresponding header contains Origin values, and if there is a browser that handles the response, we can get the response data. If the browser does not contain a direct rejection, then we cannot get the response data.

<!doctype html>
 
 

Front Cors

if (req.headers.origin) {

      res.writehead, {
        "Content-type": "text/html; Charset=utf-8 ","
        access-control-allow-origin ": ' http://localhost '/*,
        ' access-control-allow-methods ': ' Get, POST, OPTIONS ',
        ' access-control-allow-headers ': ' X-requested-with, Content-type '/
      });
      Res.write (' cors ');
      Res.end ();
    }

If we remove the Access-control-allow-origin, the browser will dismiss the response and we will not be able to get the data.

One thing to note is that the transparent server authentication mechanism for Preflighted request enables developers to use methods other than custom headers, get or post, and different types of subject content. summed up as such as:

1, not get, POST request

2. The content-type of the POST request is not a regular three: application/x-www-form-urlencoded (Forms submitted using the HTTP Post method), Multipart/form-data (Ibid., But mainly used when the form submission accompanied the file upload occasion), Text/plain (plain text)

3, the POST request payload for text/html

4, set the custom head

The options request head will contain the following headers: Origin, Access-control-request-method, Access-control-request-headers, after sending this request, The server can set the following headers to communicate with the browser to determine whether to allow this request.

Access-control-allow-origin, Access-control-allow-method, access-control-allow-headers

var xhr = new XMLHttpRequest ();
   Xhr.onload = function () {
    alert (xhr.responsetext);
   };
   Xhr.open (' POST ', ' http://localhost:8888/cors ', true);
   Xhr.setrequestheader ("Content-type", "text/html");
   Xhr.send ("F=json");

if (req.headers.origin) {

      res.writehead, {
        "Content-type": "text/html; Charset=utf-8 ","
        access-control-allow-origin ": ' http://localhost ',
        ' access-control-allow-methods ': ' Get,post,options ',
        ' access-control-allow-headers ': ' X-requested-with, Content-type '/**/
      });
      Res.write (' cors ');
      Res.end ();
    }

If you are in a debug state, you will find that the background code executes two times, indicating that two requests have been sent. Notice that our onload code only executes once, so the options request is transparent to the program and his request results are cached.

If we modify the background code to remove the Content-type, you will find that the options request failed.

The setRequestHeader (' X-request-with ', null) prevents the browser from sending the options request.

According to my test, when using Cors to send a Cross-domain request failed, the background is to receive this request, the background may also perform the data query operation, but in response to the head is not required, the browser blocked the request.

Xdr

This is a cross-domain solution provided by IE8, IE9 that only supports get and post requests, and is powerless for different cross-domain domains, such as sending HTTPS requests under the HTTP protocol. Just take a look at Microsoft's own example.

<! DOCTYPE html>  

The above is the case of Cross-domain request resources that I have encountered in the actual project, a cross-domain need to pay special attention to the HTTPS request under the HTTPS protocol, in addition to the use of proxy proxies and other methods are not solved, will be directly blocked by the browser. If a friend knows the solution, please let me know.

Finally attach the complete test demo

In ISS:

<!doctype html>
 
 

Node-html

<!doctype html>
 
 

Node-server

var http = require (' http ');
var url = require (' URL ');
var fs = require (' FS ');
var qs = require (' querystring ');

var request = require (' request ');
  Http.createserver (function (req, res) {var _url = Url.parse (Req.url);
    if (_url.pathname = = '/jsonp ') {var query = _url.query;
    Console.log (query);
    var params = qs.parse (query);
    Console.log (params);
  
    var f = "";
  
    f = params.callback;
    Res.writehead ({"Content-type": "Text/javascript"});
    Res.write (f + "({name: ' Hello World '}");
  Res.end ();
   else if (_url.pathname = = '/proxy ') {var proxyurl = "";
     if (req.url.indexOf ('? ') >-1) {Proxyurl = Req.url.substr (req.url.indexOf ('? ') + 1);
   Console.log (Proxyurl);
   } if (Req.method = = ' Get ') {Request.get (Proxyurl). pipe (RES);   else if (Req.method = = ' post ') {var POST = '; Defines a post variable that is used to suspend the request body's information Req.on (' Data ', function (chunk) {//) through the Req Data event listener function, which is added to the post variable as soon as it is received to the request body, = CH
    Unk
  
    });Post = Qs.parse (POST);
    Request ({method: ' POST ', Url:proxyurl, form:post}). pipe (RES);
   });  ' Else if (_url.pathname = = '/index ') {fs.readfile ('./index.html '), function (err, data) {Res.writehead (200, {"Content-type": "Text/html;"
      Charset=utf-8 "});
      Res.write (data);
    Res.end ();
  }); else if (_url.pathname = = '/cors ') {if (req.headers.origin) {res.writehead ({"Content-type"): "Text/html; Charset=utf-8 "," access-control-allow-origin ": ' http://localhost ', ' access-control-allow-methods ': ' Get,pos
      T,options ', ' access-control-allow-headers ': ' X-requested-with, Content-type,aaaa '/**/});
      Res.write (' cors ');
    Res.end ();

 }}). Listen (8888);

The above is the entire content of this article, I hope to help you learn, but also hope that we support the cloud habitat community.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.