PWA(Progressive Web App)入门系列:消息通讯

前言

serviceWorker 的能力决定它要处理的事情,网站页面的部分逻辑处理会转移到 serviceWorker 层进行处理,这里就要页面层和 serviceWorker 层进行交互来实现消息通讯。

下面就说一下两个环境下的消息通讯。


窗口向 serviceWorker 通讯

这里列举出窗口层到 serviceWorker 层的通讯方法。

1. ServiceWorker.postMessage

页面层可以通过 ServiceWorker 接口的 postMessage 来实现页面到 serviceWorker 环境的通讯。

ServiceWorker 接口的获取:

ServiceWorker 接口获取有两种方式

  • navigator.serviceWorker.controller,常用这种方式。
  • navigator.serviceWorker.ready.then(swReg => swReg[state]):state 为 {installing, waiting, active}

当 postMessage 后,serviceWorker 环境采用 onmessage 事件进行处理。

发送消息:

发送消息实现:

index.html

// 页面 window 环境if(navigator.serviceWorker.controller) { // 需要判断是否受控navigator.serviceWorker.controller.postMessage('消息');  // postMessage 的第一个参数可以是由结构化克隆算法处理的任何值或JavaScript对象,也包括循环引用。
}

sw.js

// serviceWorker 环境self.addEventListener("message", e => {console.log("message", e);// 从 e.data 里面取 postMessage 过来的数据
})

接收消息:

页面层 window 环境下接收消息需要在 ServiceWorkerContainer 接口上监听 onmessage:

navigator.serviceWorker.onmessage

serviceWorker 层做定向 Client 的获取有以下方式:

// 1. 通过 e.source.id 来定向发送消息self.addEventListener("message", e => {const client = await self.clients.get(e.source.id);client.postMessage('发给页面层的消息');
})// 2. 直接 e.source 来定向发送消息self.addEventListener("message", e => {e.source.postMessage('发给页面层的消息');
})

2. ServiceWorkerRegistration.sync.register

第二种方式,是使用 sync 的方式来实现页面层到 serviceWorker 层的通讯。

这种通讯的弊端是单向的,且不可控。

但优势也很明显,对于后台同步十分有用,一旦注册 sync 在 online 的状态下会立即触发 serviceWorker 环境下的 onsync 事件,serviceWorker 可根据具体逻辑处理,直到 e.waitUntil 返回 Promise.resolve() 才会完成 sync,并把 sync 的 tag 清除,否则会一直按照某个周期执行,知道 e.lastChance == true

// 页面层环境navigator.serviceWorker.ready.then(swReg => {swReg.sync.register('同步tag')
})
// serviceWorker 层环境self.addEventListener("sync", e => {if(e.tag == '同步tag') {e.waitUntil(new Promise((res, rej) => {// 逻辑处理 ...return res();}))}
})

3. MessageChannel

MessageChannel 是一个点对点的消息通道,可以很方便的实现消息的双向通讯。

构造函数:

构造函数很简单,不需要任何参数

var channel = new MessageChannel();

属性:

  • MessageChannel.port1
  • MessageChannel.port2

属性中的两个 port 为 MessagePort 接口实现,具备以下方法:

  • postMessage
  • start
  • close

具备事件监听:MessagePort.onmessage。

这里发消息时,主要以环境下的 postMessage 配合使用。

// 页面层环境if(navigator.serviceWorker.controller) {var c = new MessageChannel();c.port1.onmessage = e => {// 收到传给 port1 的消息}// 向 port2 发送消息navigator.serviceWorker.controller.postMessage('消息', [c.port2])
}
// serviceWorker 层self.addEventListener("message", e => {// 从 e.ports 里取 MessagePorte.ports[0] && e.ports[0].postMessage('向port1发送消息')
})

注意:MessageChannel 创建的通道会受 serviceWorker 的 stopWorker 影响,导致 MessageChannel 通道 close,也就是表现为通道只能用一次。所以使用 MessageChannel 通讯时,每次都要创建新的通道。


serviceWorker 向窗口通讯

上面说的是窗口页面层向 serviceWorker 环境的通讯,同样 serviceWorker 环境层也需要向页面层通讯。

在 serviceWorker 环境下主要有两种向页面层通讯的方式。

1. BroadcastChannel

第一种是 BroadcastChannel,也就是广播信道通讯。

构造函数:

构造函数很简单,channel 参数为一个字符串。

var channel = new BroadcastChannel(channel);

属性:

  • BroadcastChannel.name:构造时的信道名。

事件:

  • onmessage
  • onmessageerror

方法:

  • postMessage()
  • close()
// 页面层var bc1 = new BroadcastChannel('c1');bc1.onmessage = e => {// 页面层收到广播,逻辑处理
}
// serviceWorker 层var bc1 = new BroadcastChannel('c1');bc1.postMessage('发送广播消息');

2. client.postMessage

第二种就是获取相应的 client 进行 postMessage。

如果从 onmessage 中,是可以获取到相应的 sorce client 的,从而进行双向通讯。但在自发情况下,只能对所有 client 进行广播通讯。

// serviceWorker 环境clients.matchAll({type: "window"
})
.then(windows => {for (const win of windows) {win.postMessage('发送消息到页面');}
});

博客名称:王乐平博客

CSDN博客地址:http://blog.csdn.net/lecepin

知识共享许可协议
本作品采用知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议进行许可。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/401627.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

查看Linux上程序或进程用到的库

为什么80%的码农都做不了架构师?>>> ldd /path/to/program 要找出某个特定可执行依赖的库,可以使用ldd命令。这个命令调用动态链接器去找到程序的库文件依赖关系。 objdump -p /path/to/program | grep NEEDED 注意!并不推荐为任…

超方便的 IndexDB 库

前言 做为 Web 浏览器层的本地存储,IndexDB 做为一个很好的选择,几乎可以存储任意类型的数据,且是异步的。但是正常使用方式下需要在监听各种事件来处理结果,不是很方便,下面就对这一层进行了包装,使用方便…

BP网络识别26个英文字母matlab

wx供重浩:创享日记 对话框发送:字母识别 获取完整源码源工程文件 一、 设计思想 字符识别在现代日常生活的应用越来越广泛,比如车辆牌照自动识别系统,手写识别系统,办公自动化等等。本文采用BP网络对26个英文字母进行…

PWA(Progressive Web App)入门系列:Sync 后台同步

前言 当我们在一些地下停车场,或者在火车上、电梯等无法避免的信号不稳定的场所,使用网站应用处理一些表单操作或者上传数据的操作时,面临的将是网络连接错误的响应,使用户的操作白费。 而此刻 PWA 的 Sync API 就很好的解决了这…

PWA(Progressive Web App)入门系列:安装 Web 应用

前言 在传统的 Web 应用中,通常只能通过在浏览器的地址栏里输入相应的网址才能进行访问,或者把网页地址创建到桌面上通过点击,然后在浏览器里打开。 传统模式下,图标、启动画面、主题色、视图模式、屏幕方向等等都无法去自定义和…

「工具」IndexDB 版备忘录

前言 工作日常需要做一些备忘录,记录一些要做的事。在 Mac 上有使用系统的备忘录,但功能偏弱且文本格式调整不方便。再就是使用浏览器找专门的备忘录网站,功能是满足了,但是链路长,没有桌面软件直接。 所以最后干脆自…

「工具」PWA Manifest图标及 favicon.ico 生成工具

PWA 其中有一个能力就是把网站安装到系统桌面,以原生应用的体验来运行网站,使用户无需再找开浏览器输入网址进入网站,而是可以直接点击安装好的应用直接运行,给使网站访问缩短路径及增加网站的曝光度。 其中有一个问题就是需要生…

各种浏览器缓存浅析

前言 目前浏览器的缓存类型众多,HTTP Cache、Disk Cache、Memory Cache、ServiceWorker Cache、Push Cache 等等,这些缓存是如何产生的?命中优先级是怎么样?又该如何去使用它们? Disk Cache、Memory Cache Disk Cac…

[工具]TS 视频合并工具

简介 当下载 m3u8 资源时,通常产生的是多个 ts 视频文件,所以需要借助某些工具来将这些 ts 视频片段整合为一个视频文件。 本软件主要解决的就是这个问题,底层基于ffmpeg,可正常运行在 Windows 和 Mac 平台。不仅可以合并 ts 为单…

[会议分享]2020全球软件大会分享-PWA在项目中的最佳实践

大会地址:https://www.bagevent.com/event/1233659# PPT下载:https://download.csdn.net/download/lecepin/12871373

「浏览器插件」非常好用的JSON-View

Chrome 商店:地址 下载地址:地址 Github:https://github.com/lecepin/lp-json-view 查看/格式化 二合一。 功能 自动识别 JSON 内容,并在页面右下角创建切换按钮。支持展开/折叠节点。支持全部展开、全部折叠、展开一二三层节点…

Github Action 快速构建 Electron 应用

前言 在开发 Electron 应用时,比较耗时的部分应该是构建打包的过程,像用 electron-builder 这种打包工具来说,它会根据你要打包的系统来下载应用的系统镜像打包工具,由于这些镜像的源文件托管在 Github 上,且 nodejs …

「浏览器插件」网址小尾巴终结者

前言 在我们日常的开发调试中,会在 URL 上添加一些特殊的小尾巴 用来显示调试界面或者开启一些特殊功能,当你接触了越来越多的系统后,你需要使用的小尾巴就变得越来越多,记忆和使用成本非常大,以及含有小尾巴的网址 在…

什么是低代码?

低代码 是一种软件开发方法,可以减少手工编码的过程,尽可能快的交付应用程序。 低代码平台 是工具的合集,这些工具可以通过建模和图形界面来进行应用程序的可视化开发。低代码使开发人员可以跳过手工编码,从而加快了应用程序的开…

什么是 LOW-CODE ?

低代码平台的特征 可视化建模工具 使用可视化方法和模型创建应用程序比使用代码进行开发要快。具有可视化建模功能的低代码平台,使用内置的组件,以任何人都可读的形式表示任何信息,从没有技术技能的常规企业用户到专业开发人员。 开箱即用…

简简单单 上传下载

背景 我们经常会有手机向电脑传文件 或者 电脑像手机传文件的需求。 而通常的解决方案是:手机上安装一个聊天软件(如微信),电脑上安装一个聊天软件,然后自己给自己传输,然后进行下载。 这种方式是很麻烦的…

「VSCode插件」提效工具 - 快捷面板

前言 做为一个开发人员,在日常的开发过程中,经常会在 Terminal 中输入各种命令,如:npm i、npm start、git init、rm -rf、node_modules 等命令,看似方便,实则高频率的输入很烦人。那有什么方法可以把这些高…

VSCode摸鱼插件 — FreeWindow

背景 在一些不是很忙的时候,想高效利用下时间,看看书丰富一下自己,但是大庭广众下长时间看一本实体书,或者看手机的电子书,或者在电脑上看网页书都不太合适,显得自己很闲的样子,那该如何看起来…

在线生成文本图片 CFC函数计算版

百度云函数计算 CFC 运行环境。 使用 sharp 图处理(文档)。 使用 图片参数: widthheightrgba 文本参数: textfColorfSizefTopfLeft {HTTP触发器地址}?width1000&height300&fSize120&fColor%23d9333f&text奥利…

调试利器:浏览器 Logger

1. 前言 在一些业务系统中,由于集成的平台产物或工具较多,而这些产物的 log 不收敛,很多时候打开控制台就是满屏的 log,自己的 log 需要在满屏的 log 中查找,或者在 log 上加一些前缀用 Filter 去过滤,严重…