Open itboos opened 6 years ago
` 查看chrome 的serviceWorker
chrome://serviceworker-internals/
chrome://inspect/#service-workers ` demo: https://github.com/w3c-webmob/ServiceWorkersDemos/tree/gh-pages/game
https://developers.google.com/web/fundamentals/primers/service-workers/ 参考链接:
0: https://developer.mozilla.org/en-US/docs/Web/API/Service_Worker_API
https://www.zybuluo.com/yqlar/note/908619
Service Worker
1、Service Worker 简介
在页面中注册并安装成功后,运行于浏览器后台,不受页面刷新的影响,可以监听和截拦作用域范围内所有页面的 HTTP 请求。
1.1 Service Worker 特点
1.2 兼容性
https://caniuse.com/#feat=serviceworkers
1.3 PWA
谷歌给以 Service Worker API 为核心实现的 web 应用取了个高大上的名字:Progressive Web Apps(PWA,渐进式增强 WEB 应用),并且在其主要产品上进行了深入的实践。那么,符合 PWA 的应用特点是什么?以下为来自谷歌工程师的解答。
Progressive Web Apps 是:
2、 Service Worker 的生命周期
install -> installed -> actvating -> Active -> Activated -> Redundant
3、 使用 Service Worker
首先要注意如下两点:
A. 使用 HTTPS 访问
B. 基础知识了解:
Promise: https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Promise Promise 是 ES6 新增的规范,主要用于 javasCript 的异步处理。
Fetch API: https://developer.mozilla.org/zh-CN/docs/Web/API/Fetch_API Fetch API 用于 HTTP 请求处理,可以替代 XMLHttpRequest 实现异步请求(ajax),但功能上更为完善。
Cache API: https://developer.mozilla.org/zh-CN/docs/Web/API/Cache Cache API 用于对 HTTP 请求进行缓存管理,是在 ServiceWorker 的规范中定义的,一般也跟 ServiceWorker 一起使用,是实现离线应用的关键。但是 Cache API 又不依赖于 Service Worker,可以单独使用。
3.1、 注册
在网站页面上注册实现 Service Worker 功能逻辑的脚本。例如注册 /sw/sw.js 文件,参考代码:
注意: Service Worker 的注册路径决定了其 scope(范围) 默认作用范围。示例中 sw.js 是在 /sw/ 路径下,这使得该 Service Worker 默认只会收到 /sw/ 路径下的 fetch 事件。如果存放在网站的根路径下,则将会收到该网站的所有 fetch 事件。 如果希望改变它的作用域,可在第二个参数设置 scope 范围。示例中将其改为了根目录,即对整个站点生效。 另外应意识到这一点:Service Worker 没有页面作用域的概念,作用域范围内的所有页面请求都会被当前激活的 Service Worker 所监控。
3.2、 安装
可以看到,示例中在文件 sw.js 内监听了 install 事件。当 sw.js 被安装时会触发 install 事件,监听该事件可执行安装时要做的事情。示例中是缓存用于离线时使用的静态资源。
需要注意的是,只有 CACHE_FILES 中的文件全部安装成功,Service Worker 才会认为安装完成。否则会认为安装失败,安装失败则进入 redundant (废弃)状态。所以这里应当尽量少地缓存资源(一般为离线时需要但联网时不会访问到的内容),以提升成功率。
安装成功后,即进入等待(waiting)或激活(active)状态。在激活状态可通过监听各种事件,实现更为复杂的逻辑需求。具体参见后文事件处理部分。
event.waitUntil 相关文档解释 Cache相关文档
3.3、 Service Worker 的更新
如果 sw.js 文件的内容有改动,当访问网站页面时浏览器获取了新的文件,它会认为有更新,于是会安装新的文件并触发 install 事件。但是此时已经处于激活状态的旧的 Service Worker 还在运行,新的 Service Worker 完成安装后会进入 waiting 状态。直到所有已打开的页面都关闭,旧的 Service Worker 自动停止,新的 Service Worker 才会在接下来打开的页面里生效。
如果希望在有了新版本时,所有的页面都得到及时更新怎么办呢?
可以在 install 事件中执行 skipWaiting 方法跳过 waiting 状态,然后会直接进入 activate 阶段。接着在 activate 事件发生时,通过执行 clients.claim 方法,更新所有客户端上的 Service Worker。示例:
3.4、 fetch 事件
在安装过程中我们实现了资源缓存,安装完成后则进入了空闲阶段,此时可以通过监听各种事件实现各种逻辑。
当浏览器发起请求时,会触发 fetch 事件。
Service Worker 安装成功并进入激活状态后即运行于浏览器后台,可以通过 fetch 事件可以拦截到当前作用域范围内的 http/https 请求,并且给出自己的响应。结合 Fetch API ,可以简单方便地处理请求响应,实现对网络请求的控制。
这个功能是十分强大的。
参考下面的示例,这里实现了一个缓存优先、降级处理的策略逻辑:监控所有 http 请求,当请求资源已经在缓存里了,直接返回缓存里的内容;否则使用 fetch API 继续请求,如果是 图片或 css、js 资源,请求成功后将他们加入缓存中;如果是离线状态或请求出错,则降级返回预缓存的离线内容。
3.5、 push 事件
push 事件是为推送准备的。不过首先你需要了解一下 Notification API 和 PUSH API(相关链接见后文)。
通过 PUSH API,当订阅了推送服务后,可以使用推送方式唤醒 ServiceWorker 以响应来自系统消息传递服务的消息,即使用户已经关闭了页面。
推送的实现有两步:
不同浏览器需要用不同的推送消息服务器。以 Chrome 上使用 Google Cloud Messaging 作为推送服务为例,第一步是注册 applicationServerKey(通过 GCM 注册获取),并在页面上进行订阅或发起订阅。每一个会话会有一个独立的端点(endpoint),订阅对象的属性(PushSubscription.endpoint) 即为端点值。将端点发送给服务器后,服务器用这一值来发送消息给会话的激活的 Service Worker (通过 GCM 与浏览器客户端沟通)。
3.6、 online/offline 事件
当网络状态发生变化时,会触发 online 或 offline 事件。结合这两个事件,可以与 Service Worker 结合实现更好的离线使用体验,例如当网络发生改变时,替换/隐藏需要在线状态才能使用的链接导航等。
下面是一个监听 offline 的示例: