发布于2023-03-17 06:03 阅读(894) 评论(0) 点赞(3) 收藏(2)
一般有两种形式的跨域问题:
①使用XmlHttpRequest(XHR)或者使用AJAX发送的POST或者GET请求。这种形式的跨域是:前端页面与后端进行的跨域请求。
②父子页面之间进行的DOM操作(父子窗口之间的document操作)。这种形式的跨域是:前端页面与前端页面之间的通信或者相互操作的形成跨域。(本文主要讲这种)
iframe通信方式:
访问iframe
: contentWindow
访问父级:parent
访问顶级:top
1、不跨域:
父:
- <body>
- <textarea id="message">这是高层的密码!</textarea><br/>
- <button id="test">看看员工在说什么</button><br/><br/><br/>
- 员工们:<br/>
- <iframe src="b.htm" width="500" height="300" id="iframe"></iframe>
- <script> document.getElementById("test").onclick = function(){
- alert(document.getElementById("iframe").contentWindow.document.getElementById("message").value);
- }
- </script>
- </body>
子:
- <html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>JSONP方式</title><script type="text/javascript" src="/js/jquery-1.5.1.min.js"></script> </head>
- <body>
- <textarea id="message">这是员工的密码!</textarea><br/>
- <button id="test">看看领导在说什么</button><br/>
- <script> document.getElementById("test").onclick = function(){ alert(parent.document.getElementById("message").value); } </script>
- </body>
- </html>
使用document.domain=主域名
document.domain设置规则:
例如:当前访问地址为:https://mp.csdn.net/mp_blog/creation/editor/121540023(当前页面)。可以打开Chrome的控制台(F12)找到console的tab。默认情况下,我们输入document.domain会显示‘csdn.net’。其中csdn.net就是https://mp.csdn.net的父级域名。我们也可以设置为mp.csdn.net。因为mp.csdn.net是mp.csdn.net的同级域名。
但是我们不能设置顶级域名,即document.domain='net',就会提示错误信息。也不能设置其他的域名形式。即document.domain='csdn1.net'或者document.domain='baidu.com'。提示也说得很清楚。必须是mp.csdn.net的一个后缀形式。
注意:根据上面的设置规则,在使用document.domain的方式时,页面之间必须有相同的父级域名。否则这种方式将无法进行操作。
a.html (http://a.xxx.com/js/crossdomain/demo/a.htm)
- <html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
- <title>A</title>
- </head>
- <body>
- <textarea id="message">这是高层的密码!</textarea><br/>
- <button id="test">看看员工在说什么</button><br/><br/><br/>员工们:<br/>
- <iframe src="http://b.xxx.com/js/crossdomain/demo/b.htm" width="500" height="300" id="iframe"></iframe>
- <script>
- document.domain = "jiaju.com";
-
- document.getElementByI d("test").onclick = function(){
- alert(document.getElementByI d("iframe").contentWindow.document.getElementByI d("message").value);
- }
- </script>
- </body>
- </html>
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
b.html ((http://b.xxx.com/com/js/crossdomain/demo/b.htm ))
- <html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
- <title>JSONP方式</title>
- <script type="text/javascript" src="/js/jquery-1.5.1.min.js"></script>
- </head>
- <body>
- <textarea id="message">这是员工的密码!</textarea><br/>
- <button id="test">看看领导在说什么</button><br/>
- <script>
- document.domain = "jiaju.com";
- document.getElementByI d("test").onclick = function(){
- alert(parent.document.getElementByI d("message").value);
- }
- </script>
- </body>
- </html>
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
两个域都设置:document.domain=‘jiaju.com’
1)location.hash
location.hash
原理:
1、动态改变location.hash
,iframe
不会重载
2、无论跨域与否,iframe
内可以获取自己的location.hash
3、只要域名相同就能通信,即使ABC三层嵌套
a.html(http://www.aaa.com/demo/cross/iframe03/a.htm)嵌套了b.html(http://www.bbb.com/demo/cross/iframe03/b.html)
//父页面通过hash像子页面传值 var iframe = document.getElementByI d("iframe") 修改iframe.src改变其hash //子页面监听hash改变,获取hash上的值:window.location.hash //子页面=》父页面:要知道iframeid var hash_url = window.location.hash, datas = hash_url.split("#")[1].split("&"), data = {}; for(var i = 0;i<datas.length;i++){ var t = datas[i].split("="); data[t[0]] = decodeURIComponent(t[1]); } document.domain = "jiaju.com"; switch(data["JJtype"]) { case "height": try{top.window.document.getElementByI d(data["iframeID"]).height = data["height"];}catch(e){} break case "width": try{top.window.document.getElementByI d(data["iframeID"]).width = data["width"];}catch(e){} break case "callback": try{top.window[data["fn"]].call(document,data);}catch(e){} break default: }
location.hash
缺点
1、传递数据量有限
2、不太安全
2)window.name
location.hash
缺点
1、传递数据量有限
2、不太安全
window.name
window.name
是什么:name
在浏览器环境中是一个全局window
对象的属性
当在 iframe
中加载新页面时,name
的属性值依旧保持不变name
属性仅对相同域名的 iframe
可访问window.name
的优势:
window.name
的劣势:
iframe
的情形原理(1) :
A创建iFrame
B,把要传递的数据放入window.name
打开Chrome的控制台,当前地址为:www.baidu.com。你在console的控制台中输入window.name='moxiao',然后将当前页面的地址栏的地址改为:mai.qq.com,然后在console的控制台中打印window.name将会显示:‘moxiao’。
若父页面: parent.html;嵌在父页面的子iframe页面:child.html
1)同域时 iframe 调用父页面的JS方法
在同域的情况下,子iframe页面可以很方便地直接调用父页面定义的JS方法:window.parent.fn(); 或者 window.top.fn();
当页面中不存在 iframe 嵌套时,则 window.self, window.parent, window.top 三者均是当前窗口自身的引用。
2)不同域时 iframe 调用父页面的JS方法
不同域时上面方式调用,不报跨域错误
postMessage 的发送与接收,Window.postMessage 是 HTML5 提供的一个跨域解决方案。
1、发送:otherWindow.postMessage(message, targetOrigin, [transfer]);
2:接收:
- //event.data :传递过来的信息,也就是 postMessage 中发出的 message;
- //event.origin: 发送信息页面的域名,包括协议和端口号。
- window.addEventListener("message", function(event){
- var data = event.data;
- // 判断域名
- if(event.origin == 'http://192.168.1.237'){
- //doSomething()
- }
- });
实现:
1) child.html代码:
- <script type="text/javascript" src="sdk_child.js"></script>
- <script type="text/javascript">
- // 1)触发父页面定义的方法
- window.SDK.sayHi({msg: 'hi'});
-
- // 2)向父页面请求获取数据 uname
- var uname = '';
- window.SDK.getUname();
- setTimeout(function(){
- uname = window.SDK.uname;
- //doSomething(uname);
- }, 200);
- // 备注:发送请求后,需要延时接收返回的数据
- </script>
2) child.html 中引入的js文件 sdk_child.js 代码:
- ;(function(){
- var sdk = window.SDK || {};
- sdk.uname = null;
-
- //发送
- sdk.getUname = function(){
- window.top.postMessage({
- action: "getUname"
- }, "*")};
- sdk.sayHi = function(info){
- window.top.postMessage({
- action: "sayHi",
- info: {
- msg: info.msg
- }
- }, "*")};
- //接收
- window.addEventListener("message", function(e){
- var res = e;
- var action = res.data.action;
- var info = res.data.info;
- //判断域名
- if(res.origin == 'a.com'){
- switch (action) {
- case 'getUname' :
- sdk.uname = info;
- break;
- default :
- return
- }
- }
- });
- //写入window
- window.SDK = sdk;
- })();
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
3) parent.html 中引入的js文件 sdk_parent.js代码:
- ;(function(){
- var iframecont = document.getElementById('gameIframe').contentWindow;
- var sdk ={
- getUname: function(){
- var info = Tool.pareUrl(location.href);
- iframecont.postMessage({action: 'getUname', info: 'zhangsan'}, 'b.com');
- },
- sayHi: function(info){
- alert(info.msg);
- },
- };
-
- //监听接收
- window.addEventListener("message", function(e){
- var res = e;
- var data = e.data;
- var info = e.data.info;
- if(true){
- switch (data.action) {
- case 'sayHi' :
- sdk.sayHi(info);
- break;
- case 'getUname' :
- sdk.getUname();
- break;
- default :
- return
- }
- }
- });
- })();
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
原文链接:https://blog.csdn.net/CamilleZJ/article/details/128056333
作者:程序员的人生
链接:http://www.qianduanheidong.com/blog/article/505488/243e91457e472f7af2ca/
来源:前端黑洞网
任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任
昵称:
评论内容:(最多支持255个字符)
---无人问津也好,技不如人也罢,你都要试着安静下来,去做自己该做的事,而不是让内心的烦躁、焦虑,坏掉你本来就不多的热情和定力
Copyright © 2018-2021 前端黑洞网 All Rights Reserved 版权所有,并保留所有权利。 京ICP备18063182号-3
投诉与举报,广告合作请联系vgs_info@163.com或QQ3083709327
免责声明:网站文章均由用户上传,仅供读者学习交流使用,禁止用做商业用途。若文章涉及色情,反动,侵权等违法信息,请向我们举报,一经核实我们会立即删除!