简单的整理了jsonp跨域的发展

1.何为跨域?

妹纸我问了度娘   跨域是指一个域下的文档或脚本试图去请求另一个域下的资源,这里跨域是广义的。

妹纸觉得度娘说的对,但是也整理了自己对跨域的理解,跨域实际是浏览器的安全机制也就是同源策略作用下产生的,和服务器没有关系,

但是解决跨域问题必须是服务器允许才可以的,浏览器是不能控制跨域的

2.什么是同源策略?
同源策略/SOP(Same origin policy)是一种约定,由Netscape公司1995年引入浏览器,它是浏览器最核心也最基本的安全功能,

如果缺少了同源策略,浏览器很容易受到XSS、CSFR等攻击。所谓同源是指"协议+域名+端口"三者相同,即便两个不同的域名指向同一个ip地址,也非同源。

妹纸我盗了以个小哥哥的图看一下同源的意思

3.如何解决跨域问题呢?

很多种方法  比如 

document.domain+iframe ,window.name+iframe, 图片ping或script标签跨域 ,还有jsonp

妹纸我呢,就讲讲jsonp跨域的演化过程和原理吧

a.  首先 js的 script标签的src属性 是可以  请求跨域的文件内容, 将来会将内容, 当成js执行

html里面 <script src="http://www.xxx.com/jsonp.php"></script>
php 里面 <?php

  echo "alert('我是这里的数据’)";

?>
 
 

b.  在使用数据之前必须先引入数据,那么我们的需求是点击按钮才需要加载数据怎么办呢?当然是需要我们自己动态创建script标签啦, 想啥呢哈哈

<?php

  echo "var a = '我是你要的数据';";

?>

<button>获取数据</button> <script> var button = document.querySelector("button"); button.onclick = function() { // 动态创建script标签, 动态创建script标签加载内容是需要时间的 var script = document.createElement("script"); script.src = "http://www.xxx.com/jsonp.php"; document.body.appendChild( script );
    console.log( a );//这个a是php里面定义的数据变量
 

c.   但是当我们需要遇到数据请求的很慢的时候,js主线程已经走完了,数据还没过来 那么 这个数据在控制台打印是没定义的会报错 

没办法实时的获取数据, 满足不了点击按钮, 获取数据的需求
 
d.那就创建以个函数吧,然后把数据当做实参返回给我们
    // 定义了一个全局函数
    function func( data ) {
      console.log( data );
    }

    button.onclick = function() {
      // 动态创建script标签, 动态创建script标签加载内容是需要时间的
      var script = document.createElement("script");
      script.src = "http://www.xxx.com/jsonp.php";
      document.body.appendChild( script );
      // 请求结束, 得到结果 'php数据'; script 会将结果当成 js 执行
    }
<?php

  echo "fn('php数据')";

?>

但是呢。这个函数是死的,每次都需要定死,后台小哥哥可是很不高兴的,怎么办,

那就传一个函数过去,让后台获取,再返还回来,一般传过去的名字都会叫做callback

  // 定义了一个全局函数  
    function fn( data ) {
      console.log( data );
    }

    button.onclick = function() {
      // 动态创建script标签, 动态创建script标签加载内容是需要时间的
      var script = document.createElement("script");
      // 业内规范: 传递函数名时, 键必须叫 callback
      script.src = "http://www.xxx.com/jsonp.php?callback=fn";
      document.body.appendChild( script );
    }
<?php

  header('content-type:text/html;charset=utf-8');
  
  // 接收到前端传递过来的函数名
  $callback = $_GET['callback'];  // fn

  echo "$callback('复杂数据')";  // fndata('复杂数据')

?>

总结一下原理吧

初步演化:

1. 利用 script 标签 src 可以跨域的特性, 实现跨域请求数据

2. 就可以动态创建 script 标签, 利用src 请求 服务器端 js 内容的字符串回来

3. 将来在浏览器就可以解析执行 js 内容

后来jsonp:

前端:

1. 定义一个全局函数, 接收后台传递的数据

2. 在通过 script src 请求后台的同时, 拼接上 callback=函数名

后台:

1. 获取到通过 callback 传递过来的函数名

2. 返回函数调用(字符串), 在函数调用中, 以实参的方式将数据返回

最后妹纸我来说说jquery中的jsonp吧

 $('button').click(function() {
      // jsonp 和 ajax 没有关系的
      // jquery 将 jsonp 封装到 ajax 方法中,
      $.ajax({
        type: "post",
        url: "http://www.xxx.com/jsonp.php",
        // 指定 dataType 为 jsonp, 告诉 jquery, 我们要发送 jsonp 跨域请求
        dataType: "jsonp",
        // jsonp: "callback",
        success: function( data) {
          console.log( data);
        }
      })
    })  

原理实际一样,当你把后台数据sleep(10)睡10秒钟的时候,你会发现 jquery让浏览器做了一件事

// http://www.xxx.com/jsonp.php ?callback=jQuery112208618546570402954_1528602949160 传递给后台的全局函数名
是不是一样呀,后面那一大串就是函数名
 
好吧妹纸总结结束了,就这样吧
 

 

猜你喜欢

转载自www.cnblogs.com/wxc1991/p/9168202.html