Summary of several cross domain modes of Javascript in detail

  • 2021-07-24 09:36:44
  • OfStack

In client programming languages such as javascript, the homology policy stipulates that scripts across domains are isolated, and scripts of one domain cannot access and operate most properties and methods of the other domain. Only when two domains have the same protocol, the same host, and the same port do we assume that they are the same domain. However, in actual development, we often need to obtain resources from other domains. At this time, various cross-domain resource methods show their magical powers. Today, we mainly summarize several cross-domain methods commonly used in 1 work for query.

1.window.name

The name property of the window object is a very special property, and when a new page is loaded in frame, the value of the name property remains the same. Then we can load the page B of other domains with iframe in the page A, and assign the data to be transferred to window. name with JavaScript in the page B. After iframe is loaded, the attribute value of name can be obtained to access the information sent by Web service. However, the name property is only accessible to frame of the same domain name. This means that in order to access the name property, when the remote Web service page is loaded, you must navigate frame back to the original domain. That is, the page A modifies the address of iframe to one address in the same domain, and then the value of window. name can be read out. 1 Once the name attribute is obtained, frame is destroyed. This method is very suitable for one-way data request, and the protocol is simple and secure.

The code for page B (www. jesse. com/data. html) is as follows:


<script type="text/javascript">
window.name = 'I was there!';
//  Here is the data to be transmitted, size 1 Be general 2M , IE And firefox The next can be as large as 32M Left and right 
//  The data format can be customized, such as json , string 
</script>

The code for page A (www. jack. com/index. html) is as follows:


<script type="text/javascript">
var state = 0,
  iframe = document.createElement('iframe'),
  loadfn = function() {
    if (state === 1) {
      var data = iframe.contentWindow.name; //  Read data 
      console.log(data); // Eject 'I wasthere!'
      (function(){
        // Destroy this after getting the data iframe . 
        iframe.contentWindow.document.write('');
        iframe.contentWindow.close();
        document.body.removeChild(iframe);
      })();
    } else if (state === 0) {
      state = 1;
      //  Set up the agent page to return it to the original domain 
      iframe.contentWindow.location = "http://www.jack.com/proxy.html"; 
    }
  };
iframe.src = 'http://www.jesse.com/data.html';
if (iframe.attachEvent) {
  iframe.attachEvent('onload', loadfn);
} else {
  iframe.onload = loadfn;
}
document.body.appendChild(iframe);
</script>

2. Label with src

Although the browser disables cross-domain access by default, it does not prohibit references to files in other domains with the src attribute of tags in the page. Based on this point, complete cross-domain communication can easily be achieved by creating a node method with the src attribute. There are several cross-domain ways to use this principle:

Dynamic creation of script

For example, if I want to load the data of B from the page pageA of A, then I declare the data needed by pageA as JavaScript in the page pageB of B, and then load pageB with script tag in pageA, then the script in pageB will be executed.

The code for pageA (www. jack. com/index. html) is as follows:


function getData(data){
  // This is the related operation on the obtained data 
  console.log(data);
  // After data is obtained, remove the created script Label 
  document.body.removeChild(originData);
}
var originData = document.createElement('script');
originData.src = 'http://www.jesse.com/data.js';
originData.setAttribute("type", "text/javascript");
document.body.appendChild(originData);

The code for pageB (www. jesse. com/data. js) is as follows:


getData(' Here is the data obtained remotely across domains ');// The data format can be customized, such as json , string 

jsonp

When using $. ajax () to get remote data, if it is a cross-domain resource, you can use jsonp method. Previously, I thought jsonp was a kind of ajax, but later I realized that they were not the same thing at all. ajax requests data in xhr mode, while jsonp requests data in script mode, which is the same as the above dynamic creation of script mode 1.

The code for pageA (www. jack. com/index. html) is as follows:


$.ajax({
  //JSONP Not supported POST Mode 
  type:"GET",
  url:"http://www.jesse.com/data.php",
  dataType:"jsonp",
  // Custom jsonp Callback function name, default to jQuery Automatically generated random function name, which can also be written "?" , jQuery Will automatically process the data for you 
  jsonpCallback:"getData",
  success: function(data){
    console.log(data);
  },
  error: function(){
    console.log('fail');
  }
})

The code for pageB (www. jesse. com/data. js) is as follows:


<?php
  $callback = $_GET['callback'];// Get the callback function name , This is getData
  $data = array('a','b','c');// Data to return 
  echo $callback.'('.json_encode($data).')';// Output 
?>

3.document.domain

For the example that the main domain is the same but the sub-domain is different, it can be solved by setting document. domain. Specifically, document.domain = "a.com" can be added to http://www.a.com/a.html and http://script.a.com/b.html respectively; Then create an iframe in a. html file to control contentDocument of iframe, so that two js files can "interact". Of course, this method can only solve the situation that the main domain is the same but the second-level domain name is different

a. html on www. a. com


document.domain = 'a.com';
var ifr = document.createElement('iframe');
ifr.src = 'http://script.a.com/b.html';
ifr.style.display = 'none';
document.body.appendChild(ifr);
ifr.onload = function(){
  var doc = ifr.contentDocument || ifr.contentWindow.document;
  //  Manipulate here b.html
  alert(doc.getElementsByTagName("h1")[0].childNodes[0].nodeValue);
};

b. html on script. a. com


document.domain = 'a.com';

4. Cross-domain resource sharing (CORS)

Principle: Cross-source resource sharing (CORS) defines a cross-domain access mechanism, which enables AJAX to realize cross-domain access. CORS allows network applications on one domain to submit cross-domain AJAX requests to another domain. This function is very simple, and only one response header needs to be sent by the server. It ensures the request security by means of client + server cooperation declaration. The server will add a series of HTTP request parameters (such as Access-Control-Allow-Origin, etc.) in the HTTP request header to limit which domain requests and which request types can be accepted, while the client must declare its source (Orgin) when initiating the request, otherwise the server will not handle it. If the client does not declare, the request will even be directly intercepted by the browser and cannot reach the server. After receiving the HTTP request, the server will compare the domains, and only the requests from the same domain will be processed.

The code for pageA (www. jack. com/index. html) is as follows:


var xhr = new XMLHttpRequest();
xhr.onreadystatechange = function(){
  if(xhr.readyState === 4 && xhr.status === 200){
    console.log(xhr.responseText);
  }
};
xhr.open("get","http://www.jesse.com/data.php");
xhr.send(null);

The code for pageB (www. jesse. com/data. php) is as follows:


<?php
  header("Access-Control-Allow-Origin: http://www.jack.com");// Same as a simple request 
  header("Access-Control-Allow-Methods: GET, POST");// Methods that allow requests 
  header("Access-Control-Max-Age: 3628800"); // How long will this request be cached 
  $data = array('a','b','c');// Data to return 
  echo json_encode($data);// Output 
?>

5. window. postMesage is not commonly used

The window. postMessage (message, targetOrigin) method is a newly introduced feature of html5, which can be used to send messages to other window objects, regardless of whether the window object belongs to the same source or different sources. At present, IE8 +, FireFox, Chrome, Opera and other browsers already support window.

The code for pageA (www. jack. com/index. html) is as follows:


<script type="text/javascript">
var state = 0,
  iframe = document.createElement('iframe'),
  loadfn = function() {
    if (state === 1) {
      var data = iframe.contentWindow.name; //  Read data 
      console.log(data); // Eject 'I wasthere!'
      (function(){
        // Destroy this after getting the data iframe . 
        iframe.contentWindow.document.write('');
        iframe.contentWindow.close();
        document.body.removeChild(iframe);
      })();
    } else if (state === 0) {
      state = 1;
      //  Set up the agent page to return it to the original domain 
      iframe.contentWindow.location = "http://www.jack.com/proxy.html"; 
    }
  };
iframe.src = 'http://www.jesse.com/data.html';
if (iframe.attachEvent) {
  iframe.attachEvent('onload', loadfn);
} else {
  iframe.onload = loadfn;
}
document.body.appendChild(iframe);
</script>
0

6. location. hash is not commonly used

The code for pageA (www. jack. com/index. html) is as follows:


<script type="text/javascript">
var state = 0,
  iframe = document.createElement('iframe'),
  loadfn = function() {
    if (state === 1) {
      var data = iframe.contentWindow.name; //  Read data 
      console.log(data); // Eject 'I wasthere!'
      (function(){
        // Destroy this after getting the data iframe . 
        iframe.contentWindow.document.write('');
        iframe.contentWindow.close();
        document.body.removeChild(iframe);
      })();
    } else if (state === 0) {
      state = 1;
      //  Set up the agent page to return it to the original domain 
      iframe.contentWindow.location = "http://www.jack.com/proxy.html"; 
    }
  };
iframe.src = 'http://www.jesse.com/data.html';
if (iframe.attachEvent) {
  iframe.attachEvent('onload', loadfn);
} else {
  iframe.onload = loadfn;
}
document.body.appendChild(iframe);
</script>
1

The code for pageA (www. jack. com/proxy. html) is as follows:


<script type="text/javascript">
var state = 0,
  iframe = document.createElement('iframe'),
  loadfn = function() {
    if (state === 1) {
      var data = iframe.contentWindow.name; //  Read data 
      console.log(data); // Eject 'I wasthere!'
      (function(){
        // Destroy this after getting the data iframe . 
        iframe.contentWindow.document.write('');
        iframe.contentWindow.close();
        document.body.removeChild(iframe);
      })();
    } else if (state === 0) {
      state = 1;
      //  Set up the agent page to return it to the original domain 
      iframe.contentWindow.location = "http://www.jack.com/proxy.html"; 
    }
  };
iframe.src = 'http://www.jesse.com/data.html';
if (iframe.attachEvent) {
  iframe.attachEvent('onload', loadfn);
} else {
  iframe.onload = loadfn;
}
document.body.appendChild(iframe);
</script>
2

The code for pageB (www. jesse. com/b. html) is as follows:


function checkHash() {
  var data = '';
  // Simulation 1 Simple parameter processing operations 
  switch (location.hash) {
    case '#sayHello':
      data = 'HelloWorld';
      break;
    case '#sayHi':
      data = 'HiWorld';
      break;
    default:
      break;
  }
  data && callBack('#' + data);
}

function callBack(hash) {
  // ie , chrome The security mechanism of cannot be modified parent.location.hash , so take advantage of 1 A middle www.a.com Proxy under domain iframe
  var proxy = document.createElement('iframe');
  proxy.style.display = 'none';
  proxy.src = 'http://www.jack/c.html' + hash; //  Notice that the file is in the "www.jack.com" Under domain 
  document.body.appendChild(proxy);
}
window.onload = checkHash;


Related articles: