Bellow 是我如何注册我的 serviceworker :
if ('serviceWorker' in navigator) {
window.addEventListener('load', () => {
function updateOnlineStatus() {
SnackBar.show({
text: navigator.onLine ? onlineMsg : offlineMsg,
backgroundColor: '#000000',
actionText: close,
actionTextColor: '#d2de2f',
customClass: 'custom-snackbar',
});
}
window.addEventListener('online', updateOnlineStatus);
window.addEventListener('offline', updateOnlineStatus);
navigator.serviceWorker.register('sw.js').then((reg) => {
reg.onupdatefound = () => {
const installingWorker = reg.installing;
installingWorker.onstatechange = () => {
switch (installingWorker.state) {
case 'installed':
if (navigator.serviceWorker.controller) {
SnackBar.show({
text: refreshMsg,
backgroundColor: '#000000',
actionText: refresh,
actionTextColor: '#d2de2f',
onActionClick: () => { location.reload(); },
customClass: 'custom-snackbar',
});
} else {
console.info(availableMsg);
}
break;
case 'redundant':
console.info(redundantMsg);
break;
default:
break;
}
};
};
}).catch((e) => {
console.error(errorMsg, e);
});
});
}
这个 service-worker 是在 Workbox 构建期间生成的。
我有点担心,因为这些通知显示在我的电脑(ubuntu + chrome 59.0.3071.115
)上,但从来没有显示在我的手机上(android 6.0.1
+ chrome 59.0.3071.125
)
使用远程调试功能进行分析后,我的手机似乎onupdatefound
从未触发过。
我对 UX 感觉非常糟糕,考虑到移动设备上的访问者不知道新版本的网站正在等待中......
任何建议或意见将不胜感激
编辑 1:我在此网页的“浏览器兼容性”部分找到了更多详细信息:https ://developer.mozilla.org/en-US/docs/Web/API/ServiceWorkerRegistration/onupdatefound 。看起来 Android 版 Chrome 是否支持此功能尚不清楚。
onupdatefound
当浏览器不支持事件时,你们有一种后备/解决方法吗?
编辑 2:作为对 Jeff 的回应,
sw.js
标头在.htaccess
文件中进行管理:
<Files sw.js>
Header set Cache-Control "max-age=0, no-cache, no-store, must-revalidate"
Header set Pragma "no-cache"
Header set Expires "Wed, 11 Jan 1984 05:00:00 GMT"
</Files>
产生:
accept-ranges: bytes
cache-control: max-age=0, no-cache, no-store, must-revalidate
content-encoding: br
content-language: fr-FR
content-length: 1636
content-type: application/javascript; charset=utf-8
date: Fri, 21 Jul 2017 13:04:06 GMT
expires: Wed, 11 Jan 1984 05:00:00 GMT
last-modified: Tue, 18 Jul 2017 02:58:30 GMT
pragma: no-cache
关于您建议的工作箱微调,我还没有时间深入研究,所以我workbox-build
在 gulp 文件中使用了 easy 。但我希望会:)
// Service Worker generation
gulp.task('bundle-sw', gulp.series('generate-sitemap', () => {
return wbBuild.generateSW({
globDirectory: gulpOutputDir,
swDest: `${gulpOutputDir}/sw.js`,
globPatterns: ['**/*.{html,png,xml,css,ico,txt,json,svg,js,map,gif,jpeg,jpg,bmp,cur,webp,woff2}'],
skipWaiting: true,
clientsClaim: true,
})
.then(() => {
console.warn('Service worker generated.');
})
.catch((err) => {
console.error(`[ERROR] This happened: ${err}`);
});
}));
你认为这可能是由skipWaiting: true
?
编辑 3:尝试使用 BroadcastChannel
navigator.serviceWorker.register('/sw.js').then((reg) => {
console.log('test');
const updateChannel = new BroadcastChannel('precache-updates');
updateChannel.addEventListener('message', event => {
console.log(`Cache updated: ${event.data.payload.updatedUrl}`);
});
}).catch((e) => {
console.error(errorMsg, e);
});
即使test
在 Chrome、mobile 或 firefox 的 log 中输出,也只会在 Chrome 上抛出更新消息