1
我有一个页面和页面内的iframe。两者都托管在同一个域中。我完全控制了iframe,但没有父页面的控制权。从父窗口的上下文中的iframe的WebSocket连接
所以我需要建立从IFRAME一个WebSocket连接,但在父窗口,并保持它活着,而我从导航的iframe的背景下(到其他菜单项父页面)。
(见图片)像建立在A.html连接,并保持它活着,而导航到B和C.
这可能吗?
我有一个页面和页面内的iframe。两者都托管在同一个域中。我完全控制了iframe,但没有父页面的控制权。从父窗口的上下文中的iframe的WebSocket连接
所以我需要建立从IFRAME一个WebSocket连接,但在父窗口,并保持它活着,而我从导航的iframe的背景下(到其他菜单项父页面)。
(见图片)像建立在A.html连接,并保持它活着,而导航到B和C.
这可能吗?
简短的回答:
直接脚本注入到父窗口仍可能是一个更好的解决方案。
龙答:
的WebSocket只是一种连接到服务器。一旦你创建了它 - 它会一直存在于浏览器的标签中,如果你卸载了创建websocket的脚本,它就不会被销毁。
两个问题与iframe中,创造的WebSockets:
您可以尝试在主窗口上创建websocket工厂。这家工厂的实例将负责:
函数克隆存在一些已知问题 - 即,如果它们使用iframe脚本中定义的外部闭包 - 那么闭包将会丢失。您可能想要对克隆库进行研究。
main.js(加载在主的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);
}
一个。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>