【跨域】JSONP/CORS/降域/postMessage

浏览器的同源策略

浏览器出于安全方面的考虑,只允许与本域下的接口交互。不同源的客户端脚本在没有明确授权的情况下,不能读写对方的资源。

本域指的是?

  • 同协议:如都是http或者https
  • 同域名:如都是http://zeeliu.com/a 和http://zeeliu.com/b(要求一字不差)
  • 同端口:如都是80端口

如:

http://zeeliu.com/a/b.js 和 http://zeeliu.com/index.php (同源)

不同源的例子:

http://zeeliu.com/main.js 和 https://zeeliu.com/a.php (协议不同)
http://zeeliu.com/main.js 和 http://bbs.zeeliu.com/a.php (域名不同,域名必须完全相同才可以)
http://zeeliu.com/main.js 和 http://zeeliu.com:8080/a.php (端口不同,第一个是80)

四中跨域方法

JSONP

JSONP是服务器与客户端跨源通信的常用方法。最大特点就是简单适用,老式浏览器全部支持,服务器改造非常小。

html中script标签可以引入其他域下的js,比如引入线上的jquery库。利用这个特性,可实现跨域访问接口。需要后端支持

  • 定义数据处理函数:_fn
  • 创建script标签,src的地址执行后端接口,最后加个参数callback=_fun
  • 服务端在收到请求后,解析参数,计算返还数据,输出 fun(data) 字符串。
  • fun(data)会放到script标签做为js执行。此时会调用fun函数,将data做为参数。

代码如下

index.html代码:




  
  jsonp跨域
  


  
  • 海军首批空中女战勤加入战斗序列
  • 运20完成首次人员空运试验:乘客均为研发团队成员
  • 英媒称中国将引领科技变革:新四大发明走向全球

router.js的代码

// 注意这里的代码要放在单独的 router.js 文件中


router.get('/getNews', function (req, res) {

  var news = [
    "海军首批空中女战勤加入战斗序列",
    "运20完成首次人员空运试验:乘客均为研发团队成员",
    "英媒称中国将引领科技变革:新四大发明走向全球",
    "印巴军队交火未平息 两国代表联合国又上演舌战",
    "朝鲜的这样东西比“地震”更加震动美国人",
    "郑家概履新武警部队参谋长 接替秦天",
    "从仕途起点清除遗毒 这个落马副部问题多严重?",
    "蔡英文'朴实'午宴曝光:等于退休人员全家4天菜钱"
  ]

  var data = []
  for (var i = 0; i < 3; i++) {
    var index = parseInt(Math.random() * news.length)
    data.push(news[index])
    news.splice(index, 1) //为了避免随机到重复元素,所以push完一个就删除当前
  }

  var cb = req.query.callback
  if (cb) {
    res.send(cb + '(' + JSON.stringify(data) + ')')
  } else {
    res.send(data)
  }
})

上面index.html中

b.html


        
            
                
            

看上面的代码基本可以知道降域是怎么回事了;


下面是如何在本地建立服务器测试这个代码(包括修改hosts的内容)
首先把a.html和b.html放在同一个文件夹下
通过前面学到修改hosts的方法添加两个域名(如下图)

【跨域】JSONP/CORS/降域/postMessage_第3张图片
WX20170924-221140.png

然后在当前文件夹 mock start创建模拟服务器

没有降域情况下(document.domain被注释)

如下图
输入的地址为a.zeeliu.com:8080/a.html
虚线框窗口引用的地址是b.zeeliu.com:8080/b.html
所以左边输入aaaa右边没有变化
【这是域不同 且没有降域】

【跨域】JSONP/CORS/降域/postMessage_第4张图片
WX20170924-221303.png

如下图
当输入的地址为b.zeeliu.com:8080/a.html及时没用降域也能实现左右同步
【这是因为他们的域相同】

【跨域】JSONP/CORS/降域/postMessage_第5张图片
WX20170924-221346.png

降域情况下

如下图
通过document.domain降域后及时域名不同也可以实现效果

【跨域】JSONP/CORS/降域/postMessage_第6张图片
WX20170924-221443.png

postMessage--------------------------------------

其实就是在不降域的情况a.html向b.html发送自己想给b.html的内容;然后b.html在接受这个内容(你情我愿);反正b向a也是一样

看代码

a.html代码




  
  
  降域
  


  

使用postMessage实现跨域

b.html代码




    
    
    降域
    


    
    

你可能感兴趣的:(【跨域】JSONP/CORS/降域/postMessage)