I have a PWA built with Aurelia and compiled with Webpack, using the Workbox Plugin that generates the sw.js
service worker file. I'm trying to make the "New version available" user notification so that the user can activate the new version when clicking on a link within the app.
I am successfully downloading and installing the new version in the background, and even detecting that a new version is ready. However, when I try to call the skipWaiting()
method to force refresh of the page with the new version, it fails, because apparently I don't have the right scope or object.
The main problem is probably that I can't edit the actual sw.js because it is automatically generated. The examples all suggest the use of self.skipWaiting();
, but I don't know how to access that object.
webpack.config.js
new WorkboxPlugin({
globDirectory: './dist',
globPatterns: ['**/*.{html,js,css,woff,woff2,ttf,svg,eot,jpg}'],
swDest: './dist/sw.js',
clientsClaim: true,
skipWaiting: false, // because I want to notify the user and wait for response
}),
index.ejs
<script>
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('/sw.js')
.then(reg => {
// make the registration available globally, for access within app
window.myServiceWorkerReg = reg;
// Check for update on loading the app (is this necessary?)
return reg.update();
})
.catch(console.error);
}
</script>
app.js
activate() {
// listener for service worker update
this.swReg = window.myServiceWorkerReg;
console.warn('[app.js] ACTIVATE.', this.swReg);
this.swReg.addEventListener('updatefound', () => {
// updated service worker found in reg.installing!
console.warn('[app.js] UPDATE FOUND.', this.swReg);
const newWorker = this.swReg.installing;
newWorker.addEventListener('statechange', () => {
// has the service worker state changed?
console.warn('[app.js] STATE HAS CHANGED.', newWorker, newWorker.state);
if (newWorker.state === 'installed') {
// New service worker ready.
// Notify user; callback for user request to load new app
myUserMessage({ clickToActivate: () => {
// reload fresh copy (do not cache)
console.warn('[app.js] Post Action: skipWaiting.');
// this.swReg.postMessage({ action: 'skipWaiting' });
// THIS IS THE LINE THAT FAILS
this.swReg.skipWaiting();
}});
}
});
});
}
Everything works fine except the last line (this.swReg.skipWaiting();
). Has anyone else used webpack+workbox plugin and gotten the skipWaiting to happen as a result of user interaction?