iframe 实现跨域,两页面之间的通信

一、 背景

一个项目为vue2,一个项目为vue3,两个不同的项目实现iframe嵌入,并实现通信

二、方案

iframe跨域时,iframe组件之间常用的通信,主要是H5的possmessage方法

三、案例代码

父页面-vue2(端口号为127.0.0.1:8080)

复制代码
<template>
  <div>
    <div class="container">
      <iframe
        ref="iframeId"
        id="iframeId"
        src="http://127.0.0.1:8081"
        frameborder="0"
        border="0"
        hspace="0"
        vspace="0"
        scrolling="yes"
        height="100%"
        width="100%"
      ></iframe>
    </div>
  </div>
</template>
<script lang="ts">
import { Vue, Component } from 'vue-property-decorator';

@Component({
  components: {},
})
export default class FeatureService extends Vue {
  // 定义一个方法,用于发送消息到iframe
  private postMessageToIframe() {
    // 设置延时,确保iframe已经加载完成
    setTimeout(() => {
      // 定义要发送的数据
      const iframeInfo = { isIframeParent: true };
      // 定义目标源
      const targetOrigin = 'http://127.0.0.1:8081';
      // 获取iframe引用
      const iframe = this.$refs.iframeId;
      // 向iframe发送消息
      iframe.contentWindow.postMessage(
        JSON.stringify(iframeInfo),
        targetOrigin
      );
    }, 500);
  }

  private mounted() {
    // 在组件挂载后,发送消息到iframe
    this.postMessageToIframe();

    window.addEventListener('message', this.handleMessage, false);
  }

  private handleMessage(event: MessageEvent) {
    // 通过origin对消息进行过滤,避免遭到XSS攻击
    if (event.origin === 'http://127.0.0.1:8081') {
      console.log('子页面传输过来参数', event.data);
    }
  }
}
</script>
<style lang="less" scoped>
.container {
  width: 100%;
  margin-top: -40px;
  height: 100vh;
  overflow: hidden;
  #iframeId {
    width: 100%;
    display: block;
  }
}
</style>

子页面-vue3, (端口号为127.0.0.1:8081)

复制代码
<template>
  <div>
    <!-- 顶部导航 -->
    <TopMenu v-if="!iframeParentInfo.isIframeParent" />

    <div class="demo-sidebar-container demo-full-width">
      <!-- 侧边栏 -->
      <SiderBar v-if="!iframeParentInfo.isIframeParent" />
      <!-- 内容容器 -->
      <ContentBox />
    </div>
  </div>
</template>
<script setup lang="ts">
import { onMounted, ref } from 'vue'

const iframeParentInfo = ref({})

const messageHandler = (e) => {
  // 通过origin对消息进行过滤,避免遭到XSS攻击
  if (e.origin !== 'http://127.0.0.1:8080') return
  if (typeof e.data === 'string') {
    parseData(e.data)
  }
}

const parseData = (data) => {
  try {
    iframeParentInfo.value = JSON.parse(data)
    console.log('父页面传输过来参数', data)
  } catch (error) {
    console.error('解析JSON出错', error)
    iframeParentInfo.value = {}
  }
}

onMounted(() => {
  // 获取 父向 子(iframe) 传递的信息
  window.addEventListener('message', messageHandler)

  // 子(iframe)向父传递信息
  window.parent.postMessage('Hello Parent!', '*')
})
</script>

四、案例效果

相关推荐
ℋᙚᵐⁱᒻᵉ鲸落3 小时前
移动端滑动手势冲突:overflow: auto导致外层横向滑动失效
前端·javascript·css·vue.js·html
默_笙4 小时前
🎃 前端学了 Next.js,后端该学啥?NestJS 就是 Node 版的蜜雪冰城
前端·javascript
前端snow5 小时前
ai agent --- 实现 openclaw 定时间效果
前端
码云之上6 小时前
换模型之后,Chatbot 为什么要自己做 compact?
前端·agent·前端工程化
এ慕ོ冬℘゜6 小时前
navigator 导航对象 BOM制作方法
javascript
星栈6 小时前
自定义 UI-UX-Pro-Max 的 CSV 知识库,把 AI 生成的后台拉回行业该有的样子
前端·agent·weui
研☆香6 小时前
简单的图片上传 删除 预览
前端
ITresearchGuest6 小时前
我用 AI 一小时写了一个世界杯数据可视化平台|前端 VibeCoding 初体验
前端·人工智能·信息可视化
慧一居士7 小时前
Vite项目中使用Less步骤,详细使用示例
前端·css
花间相见8 小时前
【LangChain组件03】—— LangChain Agents 执行与状态:工作流程与状态管理实战
java·前端·langchain