作者热门文章
- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有一个页面和页面内的 iframe。两者都托管在同一个域中。我可以完全控制 iframe,但无法控制父页面。
因此,我需要从 iframe 建立一个 websocket 连接,但在父窗口的上下文中,并在我导航出 iframe(到父页面)。
(见图片)就像在 A.html 中建立连接,并在导航到 B 和 C 时保持连接。
这可能吗?
最佳答案
简答:
直接向父窗口注入(inject)脚本可能仍然是一个更优雅的解决方案。
长答案:
Websocket 只是一种与服务器的连接。一旦您创建它 - 它会一直存在于您浏览器的选项卡中,并且如果您卸载创建 websocket 的脚本,它也不会被破坏。
在 iframe 中创建 websockets 的两个问题:
您可以尝试在主窗口中创建一个 websocket 工厂。该工厂的实例将负责:
函数克隆存在一些已知问题 - 即,如果它们使用 iframe 脚本中定义的外部闭包 - 该闭包将会丢失。您可能想对克隆库进行研究。
main.js(在 main index.html 中加载):
var socketsCollection = new SocketsCollection();
function SocketsCollection() {
this.collection = {};
this.add = function(key, obj) {
if (this.exists(key)) return;
// clone websocket event handlers
// PS: this is not the best solution to clone a function. Need a better research here
eval("var onopen = " + obj.onopen.toString());
eval("var onclose = " + obj.onclose.toString());
eval("var onmessage = " + obj.onmessage.toString());
// create websocket
var ws = new WebSocket(obj.url);
ws.onopen = function(e) {
onopen(e, key, ws);
};
ws.onclose = function(e) {
onclose(e, key, ws);
}
ws.onmessage = function(e) {
onmessage(e, key, ws);
}
this.collection[key] = {
key: key,
ws: ws
};
// test websocket is alive
var self = this;
var counter = 1;
window.setInterval(function () {
console.log('testing ' + key);
self.collection[key].ws.send('ping # ' + counter + ' websocket ' + key);
counter++;
}, 2000);
}
this.exists = function(key){
return this.collection[key] !== undefined;
}
}
iframed.js:
function foo(window, socketKey) {
if (window.socketsCollection.exists(socketKey)) return;
var newSocketData = {
url: "wss://echo.websocket.org/",
onopen: function(e, key, ws) {
console.log(key + ' is OPEN', ws.readyState)
ws.send('Hello socket ' + key);
},
onclose: function(e, key, ws) {
console.log(key + ' is CLOSED', ws.readyState)
},
onmessage: function (e, key, ws) {
console.log(key + ' response: ', e.data);
}
};
window.socketsCollection.add(socketKey, newSocketData);
}
a.html:
<script src="iframed.js"></script>
<script>
foo.call(window.parent, window.parent, 'A');
</script>
b.html:
<script src="iframed.js"></script>
<script>
foo.call(window.parent, window.parent, 'B');
</script>
关于javascript - 来自父窗口上下文中 iframe 的 Websocket 连接,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46779908/
我是一名优秀的程序员,十分优秀!