[英]How to load a service worker using Webpack 5?
我正在使用 Webpack 5,我希望有一个 Service Worker 可以在不访问 .network 的情况下拦截获取请求并在本地返回响应。 我还希望能够在 Service Worker 中导入 npm 模块。 为此,我曾经使用一个名为serviceworker-webpack-plugin的库,但它不再维护,(并且在我使用它时会抛出错误)。 Webpack 文档推荐使用 Workbox,但据我所知,这似乎只是为了在 Service Worker 中缓存资产。 有人能告诉我在 2020 年使用 Webpack 5 创建 Service Worker 的正确方法是什么吗?
将 service worker 添加到您的 webpack.config.js 条目字段
entry: {
'app': "./src/index.js",
'service-worker': "./src/service-worker.ts",
},
output: {
filename: "[name].js",
},
这将发出dist/app.js
和dist/service-worker.js
,并且可以在两者中导入东西。
serviceworker-webpack-plugin
还为 serviceworker 提供了一种查看它应该缓存的所有捆绑文件列表的方法,但该功能不能直接使用,需要制作 webpack 插件才能获取。
不要过于复杂。
您只需 2 个步骤即可使 sw 工作。 创建一个软件并注册它。
创建一个 .js 文件,如sw.js
并在其中写入:
self.addEventListener('fetch', function (event) {
event.respondWith(
caches.open('mysite-dynamic').then(function (cache) {
return cache.match(event.request).then(function (response) {
var fetchPromise = fetch(event.request).then(function (networkResponse) {
cache.put(event.request, networkResponse.clone());
return networkResponse;
});
return response || fetchPromise;
});
}),
);
});
现在注册它。
if ('serviceWorker' in navigator) {
window.addEventListener('load', function() {
navigator.serviceWorker.register('/sw.js').then(function(registration) {
// Registration was successful
console.log('ServiceWorker registration successful with scope: ', registration.scope);
}, function(err) {
// registration failed :(
console.log('ServiceWorker registration failed: ', err);
});
});
}
2022答案
这在 webpack 中几乎是开箱即用的。
https://webpack.js.org/guides/progressive-web-application/
这将为您提供 webpack 正在为您处理的资产的基本缓存。
您可以获得更高级的: https ://developer.chrome.com/docs/workbox/modules/workbox-webpack-plugin/
请注意,这是使用 google 的 Workbox。 我已经在离线第一个应用程序中使用了多年,并且效果很好。
Webpack 5 应该为您开箱即用,类似于其他工作人员:
当将资产的
new URL
与new Worker
/new SharedWorker/navigator.serviceWorker.register
webpack 组合时,将自动为 web worker 创建一个新的入口点。
new Worker(new URL("./worker.js", import.meta.url))
。
选择的语法也允许在没有捆绑器的情况下运行代码。 此语法也可用于浏览器的原生 ECMAScript 模块。
(来自https://webpack.js.org/blog/2020-10-10-webpack-5-release/#native-worker-support )
对于 webpack 4,我们的 Service Worker 代码如下所示:
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
import downloadWorker from 'worker-plugin/loader!../workers/downloadHelper'
navigator.serviceWorker.register(downloadWorker).then( //...
用webpack 5,代码变成:
navigator.serviceWorker
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
.register(new URL('../workers/downloadHelper.ts', import.meta.url))
.then( // ...
我们从 webpack 5 配置中删除了worker-plugin
,v4 的代码在import
语句中使用了它。
关键是使用new URL()
- webpack 5 会将其解释为 web worker 并将为此 service worker 创建一个块并正确链接 url。
我们必须添加eslint-disable-next-line
和@ts-ignore
,因为navigator.serviceworker.register
的接口需要一个字符串,而不是URL
。 看起来 webpack 正确发送了一个字符串,但 TypeScript 似乎无法理解 TypeScript 在 webpack 运行之前运行的情况。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.