写点什么

Vue 进阶(八十六):iframe 结合 window.postMessage 实现跨域通信

发布于: 3 小时前
Vue进阶(八十六):iframe 结合 window.postMessage 实现跨域通信

一、前言

什么是iframe


iframe 元素会创建包含另外一个文档的内联框架(即行内框架)。


什么是postMessage


window.postMessage() 方法可以安全地实现跨源通信。通常,对于两个不同页面的脚本,只有当执行它们的页面位于具有相同协议(通常为https),端口号(443https的默认值),以及主机 (两个页面的模数 Document.domain设置为相同值) 时,这两个脚本才能相互通信。window.postMessage() 方法提供了一种受控机制来规避此限制,只要正确的使用,这种方法就很安全。

二、应用场景

在一个项目的页面中嵌入另一个项目的页面,需要实现父子,子父页面的通信。

2.1 嵌入页面

iframe使用如下(端口为8080):


<iframe id="myframe" name="myframe" :src="src" ref="iframe" scrolling="no" width="350px" height="350px" frameborder="0"></iframe>
复制代码


data中定义src引入端口号为 8081 的页面:


src:"http://127.0.0.1:8081/#/Login",
复制代码


那么问题就来了,嵌入的登录模块属于子页面(另一个项目,端口号 8081)的东西,如何能让我自己的页面知道用户点击了蓝色按钮,达到登录后隐藏登录框的效果呢?在这里,postMessage就派上了用场。

2.2 postMessage 实现父子页面通信

window.postMessage中的windowiframe中是指什么呢?



我们首先要获取到iframecontentWindow属性放到mounted钩子函数中。


mounted() {  this.iframeWin = this.$refs.iframe.contentWindow;},
复制代码


目标源写成 * ,具备了两个必要参数,我们就可以开始使用postMessage了。

2.3 子页面向父页面传值

在这个项目中,我需要在点击 login 按钮(子页面),并且登陆成功后在父页面中隐藏登录模块。


父页面如何才能知道用户点击了子页面按钮?


postMessage只是一个沟通的桥梁。


子页面说话,父页面需要听到。所以我们在父页面的 mounted 函数中写一个监听。


mounted() {    window.addEventListener('message', this.handleMessage);    this.iframeWin = this.$refs.iframe.contentWindow;},
复制代码


下面为完整代码


子页面代码:


 submit() {   // 向父vue页面发送信息   window.parent.postMessage({     data: {       code:"success",       test:"我是子页面的test!"     }   }, '*'); }
复制代码


父页面代码:


<div class="login" v-if="!loginStatus">   <iframe id="myframe" name="myframe" :src="src" ref="iframe" scrolling="no" width="350px" height="350px"  frameborder="0"></iframe></div> methods: {     handleMessage (event) {       const data = event.data.data        if(data.code === "success"){            alert(data.test)        }     }}
mounted() { window.addEventListener('message', this.handleMessage); this.iframeWin = this.$refs.iframe.contentWindow;},
复制代码

2.4 父页面向子页面传值

父页面代码:


sendMessage () {   // 外部vue向iframe内部传数据   this.iframeWin.postMessage({   cmd: 'success',   data: "我是来自父页面的data!"}, '*')
复制代码


子页面监听同理。

三、拓展阅读

发布于: 3 小时前阅读数: 2
用户头像

No Silver Bullet 2021.07.09 加入

岂曰无衣 与子同袍

评论

发布
暂无评论
Vue进阶(八十六):iframe 结合 window.postMessage 实现跨域通信