当 iframe 在不同的域 iframe 中时,获取相同域 iframe 的高度?
Posted
技术标签:
【中文标题】当 iframe 在不同的域 iframe 中时,获取相同域 iframe 的高度?【英文标题】:Get the height of a same domain iframe when that iframe is inside a different domain iframe? 【发布时间】:2017-10-20 02:04:19 【问题描述】:我有一个网站,它在 iframe 中嵌入了媒体播放器。媒体播放器和站点在同一个域中,防止跨域问题。每个页面,主页面以及媒体播放器页面,都有一些代码可以找到任何父 iframe 的高度和宽度:
var height = $(parent.window).height();
var width = $(parent.window).width();
到目前为止没有问题......直到:
一位客户希望将我的网站嵌入到他自己网站的 iframe 中。他的网站位于不同的域中。现在,我的 iframe 在另一个 iframe 中,我的代码抛出了跨域错误。
以下不会抛出错误:
var test1 = parent.window; // returns my site
var test2 = window.top; // returns client site
以下确实会引发跨域错误:
var test3 = parent.window.document;
var test4 = $(parent.window);
var test5 = window.top.document;
var test6 = $(window.top);
如何在不出现跨域错误的情况下获取域中 iframe 的高度?我希望有一个纯 javascript/jQuery 解决方案。
不适用于我的解决方案的选项是:
-
使用 document.domain 将站点列入白名单。
修改 web.config 以将该站点列入白名单。
就像在《盗梦空间》中一样,我必须更深入。请帮忙。
【问题讨论】:
【参考方案1】:您需要使用Javascript's messager。首先,你需要像这样定义一个function
:
function myReceiver(event)
//Do something
那么你需要一个事件监听器:
window.addEventListener("message", myReceiver);
两边都需要这样的东西。现在,您可以向iframe
发送这样的消息:
innerWindow.contentWindow.postMessage( message: ResponseKey: "your response key", info1: "something1", info2: "something2", innerWindow.src)
这就是您可以向父母发送消息的方式:
window.parent.postMessage( message: ResponseKey: "your response key", info1: "something1", info2: "something2", myorigin);
谜题中唯一缺少的项目是myorigin
。您可以在消息接收者事件中使用event.origin || event.originalEvent.origin
在您的iframe
中找到它。
但是,在 iframe
内的页面中使用您网站的页面必须包含一个 Javascript 库,该库将处理您所需的通信。我知道这项研究有多痛苦,我已经花了好几天的时间才找到答案。
【讨论】:
我喜欢使用它来反转控制的想法。当我的父页面有页面 resize() 事件时,它可以向子 iframe 页面发送新尺寸的消息。【参考方案2】:您的代码从父窗口和子窗口中间的 iframe 运行。所以,只要你打电话
window.parent
如果您的网站嵌入在 iframe 中,并且父级是不同的域(同源策略),则会引发错误。我建议首先检查父母是否是同一来源。您需要将此检查包装在 try catch 中。
注意:如果父级是 http://localhost:xxx 并且 iframe 是 http://localhost:zzz 其中 xxx 是与 zzz 不同的端口号,大多数浏览器,但不是 Edge,不会抛出错误。因此,您还需要通过比较协议、域和端口来手动检查源匹配。
var isEmbeddedInCrossOriginIframe = false;
try
var originSelf = (window.self.location.protocol + '//' +
window.self.location.hostname +
(window.self.location.port ? ':' +
window.self.location.port : '')).toLowerCase();
var originParentOrSelf = (window.parent.location.protocol + '//' +
window.parent.location.hostname +
(window.parent.location.port ? ':' +
window.parent.location.port : '')).toLowerCase();
isEmbeddedInCrossOriginIframe = originSelf != originParentOrSelf;
catch(err)
isEmbeddedInCrossOriginIframe = true;
//console.log(err);
您的解决方案将是:
var height = $(isEmbeddedInCrossOriginIframe ? window : parent.window)
.height();
var width = $(isEmbeddedInCrossOriginIframe ? window : parent.window)
.width();
【讨论】:
以上是关于当 iframe 在不同的域 iframe 中时,获取相同域 iframe 的高度?的主要内容,如果未能解决你的问题,请参考以下文章