浏览器窗口间通讯

浏览器窗口间通讯

浏览器多个标签页窗口间通讯,主要是指的同源的多个页面间的通讯,主要方法有本地存储通讯、Web Worker通讯、Web Socket通讯。javascript

本地存储通讯

经过浏览器对于同源页面本地存储是共享的策略实现通讯,主要可使用localStoragecookieindexDB,注意对于sessionStroage是在同一会话有效的,在MDN中提到,经过点击连接或者使用window.open打开的新标签页之间是属于同一个session的,新的标签页会继承上一级会话的sessionStroage,但新开一个标签页老是会初始化一个新的session,即便是同源的,它们也不属于同一个sessionhtml

localStorage

// 页面A
localStorage.setItem('msg', Math.random());
// 页面B
window.addEventListener("storage", function (e) {
  console.log(e);
})
// onstorage事件
// 非当前页面对localStorage进行修改时才会触发,当前页面修改localStorage不会触发监听函数
// 在对原有的数据的值进行修改时才会触发监听函数,当新设值与原有值相同时不会触发。
// 页面A
document.cookie = "msg=1;path=/";
// 页面B
function getCookie(key){
    var cookies = {};
    document.cookie.replace(/\s*/g,"").split(";").forEach((v) => {
        let unit = v.split("=");
        cookies[unit[0]] = unit[1];
    })
    return cookies[key];
}
setInterval(() => {
    console.log(getCookie("msg"));
}, 1000);

IndexedDB

// 页面A
var db = null;
var request = indexedDB.open("message");
request.onsuccess = (e) => db = e.target.result;
request.onupgradeneeded = function(event) {
    db = event.target.result;
    if (!db.objectStoreNames.contains('message')) {
        db.createObjectStore('message', { keyPath: 'key' });
    }
};

function setData(data){
    var transaction = db.transaction(['message'], 'readwrite');
    var store = transaction.objectStore(['message']);
    var requestData = store.put({ key: "msg", info: data});
    requestData.onsuccess = function(e) { 
        console.log(e.target.result);
    };
};

setTimeout(() => setData(1),1000);
// 页面B
var db = null;
var request = indexedDB.open("message");
request.onsuccess = (e) => db = e.target.result;
function readMsg(){
    var transaction = db.transaction(['message']);
    var objectStore = transaction.objectStore('message');
    var requestResult = objectStore.get('msg');

    requestResult.onsuccess = function(event) {
        console.log(requestResult.result.info);
   };
}

setTimeout(readMsg, 3000);

Web Worker

HTML5中的Web Worker能够分为两种不一样线程类型,一个是专用线程Dedicated Worker,一个是共享线程Shared Worker
Dedicated Worker直接使用new Worker()便可建立,这种webworker是当前页面专有的。
SharedWorker能够被多个window、标签页、iframe共同使用,但必须保证这些标签页都是同源的。java

// 页面A
var worker = new SharedWorker('worker.js');
worker.port.start();
worker.port.postMessage(1);
// 页面B
var worker = new SharedWorker('worker.js');
worker.port.start();
worker.port.onmessage = function(event){
    console.log(event.data);
};
// worker.js
var portArr = [];
onconnect = function(e) {
  var port = e.ports[0];
  if(portArr.indexOf(port) === -1) portArr.push(port);
  port.onmessage = function(e) {
    portArr.forEach( v => {
        v.postMessage(e.data);
    })
  }
}

Web Socket

使用Web Socket将服务器做为数据中转站进行数据传输,能够实现浏览器窗口间通讯,可是比较耗费服务器资源。WebSocketHTML5开始提供的一种在单个TCP链接上进行全双工通信的协议。WebSocket 使得客户端和服务器之间的数据交换变得更加简单,容许服务端主动向客户端推送数据。在 WebSocket API中,浏览器和服务器只须要完成一次握手,二者之间就直接能够建立持久性的链接,并进行双向数据传输。在WebSocket API中,浏览器和服务器只须要作一个握手的动做,而后,浏览器和服务器之间就造成了一条快速通道,二者之间就直接能够数据互相传送。git

  • 握手阶段采用HTTP协议,在普通HTTP报文中包含了一些附加头信息,其中附加头信息Upgrade: WebSocket代表这是一个申请协议升级的HTTP请求。
  • 创建在TCP协议基础之上,和HTTP协议同属于应用层。
  • 能够发送文本,也能够发送二进制数据。
  • 数据格式比较轻量,性能开销小,通讯高效。
  • 没有同源限制,客户端能够与任意服务器通讯。
  • 协议头标识符是ws,若是加密传输则为wss

每日一题

https://github.com/WindrunnerMax/EveryDay

参考

https://github.com/lmk123/blog/issues/66
https://www.cnblogs.com/cloud-/p/10713213.html
https://www.cnblogs.com/lalalagq/p/9921144.html
相关文章
相关标签/搜索