服务工人
对无法设置响应头的静态主机进行交叉原生隔离,
例如GitHub Pages。 服务员加头
(单位:千美元)Cross-Origin-Opener-Policy: same-origin, (中文(简体) ),
Cross-Origin-Embedder-Policy: require-corp对它所服务的每一个反应,所以
页面可以使用 SharedArrayBuffer 和需要其他API的
window.crossOriginIsolated。 。 。 .
使用量
复制 coi-serviceworker.js 在您的页面旁边, 在脚本之前加载
这需要隔离:
<script src="coi-serviceworker.js"></script>
从文件中装入作为经典脚本. 与 type="module",或与
代码内置,脚本无法找到自己的 URL,所以它会登录一个警告
保持原样.
服务员只控制自己的文件夹和下面的文件夹,所以
将文件放在需要的每页或以上, 以及每页或以上
Worker 脚本这些页开始。 工人的范围
脚本的URL服务于该脚本,而不是控制页面的. 一个工人
范围外的脚本没有 Cross-Origin-Embedder-Policy,则
孤立页面的浏览器在页面本身仍然报告时屏蔽它
crossOriginIsolated测试 a worker script outside the scope is blocked 显示这个.
从 npm :
npm install @aletheia-works/coi-serviceworker
cp node_modules/@aletheia-works/coi-serviceworker/coi-serviceworker.js public/
JSR 上的文件为
@aletheia-works/coi-serviceworker。 。 。 .
页面必须在 HTTPS 上或从 localhost。每个交叉来源
资源必须允许嵌入( CORS 或
Cross-Origin-Resource-Policy),作为 require-corp 需求.
等待隔离
脚本集 window.coiServiceWorker 只要它运行, 所以稍后
脚本可以等待, 而不是用超时猜测 :
const state = await window.coiServiceWorker.settled;
if (state.status === 'isolated') startTheWork();
else if (state.status === 'failed')
console.error('not isolated:', state.reason);
settled 一旦页面被隔离,就解决({ status: 'isolated' }),已经
失败( e){ status: 'failed', reason })或已经将工人带走
(单位:千美元){ status: 'unregistered' },见下文)。 它从来没有解决 在一页
即将重新装入,所以没有重的开始在那里. coiServiceWorker.status
是当前状态 : pending, (中文(简体) ), reloading, (中文(简体) ), isolated, (中文(简体) ), failed 或者说
unregistered。每个更改也作为 coi-serviceworker 活动
window,以国家为主 detail。在一个孤立的页面上,当
注册前脚本失败, 事件会同时发送脚本本身
运行, 因此一个后期剧本添加的收听器会错过它 。 其他活动也来了
以后,但也许仍然来之前 一个慢剧本听,所以读 status
或等待时间 settled 而不是依赖于事件.
Npm 软件包持有类型 。 参考文献 globals 键入
window.coiServiceWorker 和事件,并按名称导入其余部分:
/// <reference types="@aletheia-works/coi-serviceworker/globals" />
import type { CoiFailure } from '@aletheia-works/coi-serviceworker/coi-serviceworker.js';
JSR一揽子出口 CoiServiceWorker, (中文(简体) ), CoiState, (中文(简体) ), CoiSettled 财务报告和审定财务报表
CoiFailure 而不是全球,因为JSR拒绝 declare global。 。 。 .
写你自己的.
reason | 原因 |
|---|---|
module-script | 脚本装入 type="module",或内置 |
no-service-worker | 没有安全的环境,或者没有服务工作者的支持 |
registration-failed | navigator.serviceWorker.register 被拒绝 |
outside-scope | 这页不在工人的范围之内 |
storage-unavailable | 会话存储已丢弃, 因此没有重新装入页面 |
still-not-isolated | 这页是经过工人的 还没有被隔离 |
unexpected-error | 其它抛出的东西; 警告显示错误 |
限制它隔离的页面
一旦登记,工人将隔离其范围内的每一页,包括:
从未加载脚本的页面,其跨源资源必须
然后允许被嵌入。 只隔离一些页面, 请用
include,作为路径前缀,在脚本的URL中. 可重复如下:
<script src="/coi-serviceworker.js?include=/app/&include=/demo.html"></script>
然后,该工人只在这些路径下的页上加上标题,并且
这些页提出的要求,包括: Worker 他们开始的脚本.
瞄准镜上的其他页面,好像工人不在一样。 一页
加载脚本本身必须置于前缀之下:否则将重新加载
一次并结束 failed 与 still-not-isolated。每个装入
脚本应该使用相同的 URL, 因为注册另一个 URL 取代
整个范围的工人。 老工人没有隔离的一页
重新装入一次通过新的.
清除工人
工地停止装入脚本后 工人会继续登记
继续隔离其范围内的页面。 装入脚本 unregister
在该范围内删除的页面中:
<script src="/coi-serviceworker.js?unregister"></script>
剧本未注册 每一个注册的工人是这个剧本,在
无论登记的范围如何,如果该工人服务,则重新加载页面
,并设置状态为 unregistered。WebKit仍然可以服务于第一个
通过被移除的工人重新装入,然后页面再次被重新装入.
在一个框架
Iframe中的一页仅在嵌入的一页被横出处隔离 它也是孤立的.
- 如果同一来源上的母页加载了脚本,则母页和 框架都是孤立的.
- 如果只装入了帧,则帧不被隔离并记录出警告. 如果母页在工人的范围之内, 两者都隔离一次 父重装。 如果它在外面, 框架永远不会被隔离 警告人们.
- 另一个来源上的一页无法嵌入此套件隔离的一页 。 如果 父目录不会发送孤立标题,也不会发送孤立页。 如果是这样, 浏览器不装入框架.
拜访时会发生什么事
- 该页面已经被跨源隔离(服务器发送信头,
或服务于它的工人:
isolated,没有其他的 发生. - 否则剧本就登记为服务员 等到 工人们 活动,然后重新装入页面一次。 重新装入的页面 穿过工人 被隔离 如果脚本被装入 模块,或者注册失败,它会记录一个警告而不重新装入.
- 如果重新装入的页面仍未被隔离,则脚本会记录一个警告和 不再重新装入。 后来的硬重装 跳过工人,是 重新装入工人,除非在一秒内开始 上次重装.
- 如果无法进行会话存储, 脚本无法标记重装, 所以 它登记工人,记录一个警告,而不重新装入。 页面是 与下一个负载隔离.
以后的探视从一开始由工人提供服务,不需要重新装入.
与gzuidhof/coi-service工人的差异
这套方案是独立执行以下概念: gzuidhof/合作社服务员, (中文(简体) ), 他们最后的一次发布,0.1.7是2023年的.
- 发现工人安装后,立即重新装入,然后装入
活动。 当安装需要一点时间, 重新装入的页面被装入
没有工人,就不再被隔离,也不再重新装入。 这个
软件包仅在之后重新装入
navigator.serviceWorker.ready测试a worker that is slow to install still isolates the page失败针对 0.1.7和通过这里. Cross-Origin-Embedder-Policy总是require-corp;没有credentialless模式.- 没有
window.coi配置 。 脚本的 URL 需要include财务报告和审定财务报表unregister相反,和window.coiServiceWorker仅报告 状态.
发展
工具来自 mise.toml (单位:千美元)mise install) (中文(简体) ).
bun install
mise run check
mise run test
mise run test 使用 Bun 服务测试页面并运行 Playwright 测试
Chromium, Firefox and WebKit (英语:Firefox and WebKit (film))). 克林姆,火狐和WebKit.
释放
常规公约 main 驱动释放请。 合并其发布 PR
创建 v<version> 标签,以及 publish.yml 将软件包发布到 npm
和JSR与OIDC信任的出版和出处.
许可证
阿帕奇 - 2.0