js iframe跨域访问

Posted 快饿死的鱼

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了js iframe跨域访问相关的知识,希望对你有一定的参考价值。

1.什么是跨域?
2.前台解决跨域几种方法
  2.1 动态创建script
  2.2 使用document.domain
  2.3使用html5新属性postMessage
  2.4 利用iframe和location.hash
 
 
什么是跨域?
....................................................................................................................................................................................
javascript处于安全方面的考虑(同源策略限制),不允许跨域调用其他页面的对象。
也就是“Domains,protocols,posts”不一样就是跨域。
“Domains”就是指的域名,
“protocols”就是协议,分为http和https,
“ports”就是端口名称
需要注意的是:
  1.如果是protocols和ports不一致造成的跨域,前台没有办法解决
  2.域只通过URL的首部,也就是protocols+domain+port来判断是否跨域,不会去判断domain是否对应着相同的IP地址
    因此就出现如下几种跨域情况:
 
 
URL 说明 是否跨域

http://www.a.com/a.js

http://www.a.com/b.js

同protocol,domain,port 允许

http://www.a.com/a/a.js

http://www.a.com/b/b.js

同protocol,domain,port,不同文件夹 允许

http://www.a.com:8000/a.js

http://www.a.com/b.js

同protocol,domain,不同port(默认port:80) 不允许

http://www.a.com/a.js

https://www.a.com/b.js

同domain,port,不同protocol 不允许

http://www.a.com/a.js

http://192.168.82.45/b.js

同protocol,port,不同domain 不允许

http://www.a.com/a.js

http://child.a.com/b.js

主域相同(a.com),子域不同(www,child) 不允许

http://www.a.com/a.js

http://a.com/b.js

一级域名相同,二级域名不同(同上) 不允许

http://www.a.com/a.js

http://www.b.com/b.js

同protocol,port,不同domian 不允许
解决方法
......................................................................................................................................................................................
1.动态创建script标签
  虽然浏览器默认阻止跨域请求,但是不阻止在页面中引用其他域的文件。
  因此可以动态添加script标签。JSONP就是利用这一原理来实现ajax跨域的
 
2.通过修改docment.domain来实现跨域
  该方法必须是在同主域,不同子域的情况下才生效
  比如:morningstar.com 和test.morningstar.com
只要把两个页面 的document.domain都指向主域就可以了,比如document.domain=\'morningstar.com\'
<!-- morningstar.com/parent.html -->
<iframe id="ifr" src="http://test.morningstar.com/MarketBarometer/html/test.html" width="200px"></iframe>
<script>document.domain = \'morningstar.com\';
functionaa(str){
    console.log(str);
}
window.onload = function(){
    document.getElementById(\'ifr\').contentWindow.bb(\'aaa\');
}
</script>
<!--test.morningstar.com/test.html --><script>document.domain = \'morningstar.com\';
functionbb(str){
    console.log(str);
}

parent.aa(\'bbb\');
</script>

 

3.通过HTML5 postMessage
  不同域之间的跨域请求  使用postMessage。postMessage是HTML5新增的方法,简单易用高大上
  比如:test.com 和qsstage.morningstar.com

.postMessage(message,targetOrigin)参数说明

message: 是要发送的消息,类型为 String、Object (IE8、9 不支持)
targetOrigin: 是限定消息接收范围,不限制请使用 \'*\'

\'message\',function(e)回调函数第一个参数接受Event对象,有三个常用属性:

data: 消息
origin: 消息来源地址
source: 源 DOMWindow 对象

一个简单的父页面qsstage.morningstar.com/parent.html 和子页面 test.com/test.html建立通信

<!-- qsstage.morningstar.com.com/parent.html --><iframeid="ifr"src="http://bar.com/b.html"></iframe><script>window.onload = function(){
    var ifr = document.querySelector(\'#ifr\');
    ifr.contentWindow.postMessage({a: 1}, \'*\');
}
window.addEventListener(\'message\', function(e){
    console.log(\'bar say: \'+e.data);
}, false);
</script>
<!-- test.com/test.html -->
window.addEventListener(\'message\', function(e){
    console.log(\'foo say: \' + e.data.a);
    e.source.postMessage(\'get\', \'*\');
}, false)

 

  

 

4.iframe+location.hash解决跨域
  利用代理页面来解决HTML iframe跨域访问  使用location.hash.
  通过URL传递数据。
  结构关系:chart/com
                      ---parent.html
                      ---poxy.html
      test.com
                  ---child.html

一个简单的父页面chart.com/parent.html 和子页面 test.com/child.html建立通信,通过chart.com/poxy.html实现跨域访问

<!-- chart.com/parent.html -->
<iframe id="test1" src="http://test.com/test.html" width="100%" height="200px"></iframe>
    <script>
        function callback(data) {
            console.log(data);
        }
    </script>

 

<!-- chart.com/poxy.html -->
<script type="text/javascript">
        window.onload = function () {
            var data = location.hash.substr(1);
            data = eval("(" + decodeURIComponent(data) + ")");
            top.document.getElementById("test1").style.height = data.height + \'px\';
            //调用父页面方法,可不写
            top.callback(data);
        }
    </script>

 

 
<!-- test.com/child.html -->
 <div style="height:400px">
        <p>我是子页面</p>
    </div>
    <script type="text/javascript">
       
        window.onload = function () {
            if (!document.getElementById("crossFrame")) {
                var iframe = document.createElement(\'iframe\');
                iframe.setAttribute(\'style\', \'width:100%\');
                iframe.setAttribute(\'src\', \'http://chart.com/poxy.html\');
                var height = document.documentElement.scrollHeight;
                var data = \'{height:\' + height + \'}\';
                //通过参数传递高度heights
                iframe.src = \'http://chart.com/poxy.html#\' + data;
                document.body.appendChild(iframe);
            } else {
                document.getElementById("crossFrame").src = url;
            }
        }
    </script>

 

以上是关于js iframe跨域访问的主要内容,如果未能解决你的问题,请参考以下文章

iframe跨域访问父框架js方法

js iframe跨域访问

如何用javascript 跨域获取iframe子页面的元素信息

如何解决js跨域问题

跨域访问和同源策略

iframe与主框架跨域相互访问方法