美文网首页
前端跨页面通信 的几种思路

前端跨页面通信 的几种思路

作者: 爱学习的小仙女早睡早起 | 来源:发表于2023-08-07 16:38 被阅读0次

    同源页面

    A页面打开B页面,B页面的业务进行完成后,B页面需要触发A页面的某刷新方法

    广播模式,页面将消息通知给一个中转,中转再通知给各个页面。中转可以是一个 BroadCast Channel 实例、一个 Service Worker 或是 LocalStorage。

    BrocastChannel

    BrocastChannel可以实现同源下浏览器不同窗口,tab页,frame或frame下的浏览器上下文之间的通信。

    // a页面
    var bc = new BroadcastChannel('qwer')
    bc.postMessage('发送数据')
    
    // b页面
    var bc = new BroadcastChannel('qwer')
    bc.onmessage = function(e) {
      console.log(e)
    }
    /** 消息发送后,所有连接到该频道的 BrocastChannel对象上都会触发 meaasge事件,
    该事件没有默认行为,可以使用`onmessage`事件处理程序来定义一个函数处理消息
    **/
    

    LocalStorage

    LocalStorage是前端常用的本地存储,当LocalStorage变化是,会触发storage事件,发送消息时,将消息写入LocalStorage中,然后在各个页面中,通过监听storage事件即可收到通知。

    // a页面
    window.addEventListener('storage', function(e) {
      console.log(e)
    })
    
    // b页面
    localStorage.setItem('qwer', 10000)
    



    1、A页面的mounted里监听

        let CHANNEL_CODE = 'refreshTable'
        this.listenChannel = new BroadcastChannel(CHANNEL_CODE);
        this.listenChannel.onmessage = (res) => {
            // console.log(res);
            if (res.data.success) {
                that.bs.queryTableList();
            }
        };
    
    
    // 注意在A页面里这里要销毁
    beforeDestory(){
        this.listenChannel.close();
    }
    

    2、B页面触发

            let CHANNEL_CODE = 'refreshTable'
              let listenChannel = new BroadcastChannel(CHANNEL_CODE);
              listenChannel.postMessage({
                type: 'refreshTable',
                success: 'true' + Math.random()
              });
              console.log("触发刷新数据" )
              listenChannel.close();
    

    Vuex

    如果是vue项目
    还可以考虑将监测数据存入到store里,在A页面的computed拿到检测数据,然后watch数据的变化;


    或者在浏览器缓存存储检测数据,在A页面定时器获取检测数据来判断变化

    通过事件的发布订阅模式

    代码实现
    utils/msgCenter.js

    class msgCenter {
        constructor() {
    
        }
    
        msgObj = new Object();
    
        on = (msgName, func) => {
            this.msgObj[msgName] = func;
        }
    
        one = (msgName, func) => {
            this.msgObj[msgName] = func;
        }
    
        emit = (msgName, data) => {
            if (!Object.prototype.hasOwnProperty.call(this.msgObj, msgName)) return;
            this.msgObj[msgName](data);
    
        }
    
        off = (msgName) => {
            if (!Object.prototype.hasOwnProperty.call(this.msgObj, msgName)) return;
            delete this.msgObj[msgName];
        }
    
    }
    
    export default new msgCenter()
    

    使用:

    发布事件
                  import $SLMC from "@/utils/msgCenter";
    
                  $SLMC.emit("refreshTable", data);  
    
    
    订阅事件
                  import $SLMC from "@/utils/msgCenter";
    
                  $SLMC.on("refreshTable", this.refreshTable);
    

    相关文章

      网友评论

          本文标题:前端跨页面通信 的几种思路

          本文链接:https://www.haomeiwen.com/subject/mspgpdtx.html