chrome://flags/#unsafely-treat-insecure-origin-as-secure
https://example.test
Relaunch
config.force_ssl = true
serviceworker-rails
install
, activate
, fetch
event.waitUntil()
accepts a promies that MUST be successful in order for the service worker to be installedcaches.open()
returns a promise that adds the static offline assets to a named cache associated with the site and the user's browserGET
requests to the hostapplication.js
, be sure to include navigator.serviceWorker.register('/serviceworker.js');
{
"name": "Alloy Application Demo",
"short_name": "Alloy",
"description": "An Episerver site with PWA added",
"start_url": "/",
"display": "standalone",
"orientation": "any",
"background_color": "#fff",
"theme_color": "#fff",
"icons": [
{
"src": "/static/img/icons8-ios-app-icon-shape-72.png",
"sizes": "72x72",
"type": "image/png"
},
{
"src": "/static/img/icons8-ios-app-icon-shape-152.png",
"sizes": "152x152",
"type": "image/png"
},
{
"src": "/static/img/icons8-ios-app-icon-shape-192.png",
"sizes": "192x192",
"type": "image/png"
},
{
"src": "/static/img/icons8-ios-app-icon-shape-256.png",
"sizes": "256x256",
"type": "image/png"
},
{
"src": "/static/img/icons8-ios-app-icon-shape-512.png",
"sizes": "512x512",
"type": "image/png"
}
]
}
// File is executed in the background without needing connection
// ASYNCHRONOUS
if ('serviceWorker' in navigator) {
window.addEventListener('load', function () {
navigator.serviceWorker.register('/sw.js').then(function (reg) {
console.log('Registered Service Worker for Alloy');
});
});
}
// Install event
self.addEventListener("install", function(e) {
console.log("Alloy service worker installation");
e.waitUntil(
caches.open(cacheName).then(function(cache) {
console.log("Alloy service worker caching dependencies");
initialCache.map(function(url) {
return cache.add(url).catch(function(reason) {
return console.log(
"Alloy: " + String(reason) + " " + url
);
});
});
})
);
});
// Activate Event
// Runs after the install event and page refresh
self.addEventListener("activate", function(e) {
console.log("Alloy service worker activation");
e.waitUntil(
caches.keys().then(function(keyList) {
return Promise.all(
keyList.map(function(key) {
if (key !== cacheName) {
console.log("Alloy old cache removed", key);
return caches.delete(key);
}
})
);
})
);
return self.clients.claim();
});
// Fetch Event
// Allows for offline functionality
// Returns results fom the cache when offline
self.addEventListener("fetch", function(e) {
if (new URL(e.request.url).origin !== location.origin) return;
if (e.request.mode === "navigate" && navigator.onLine) {
e.respondWith(
fetch(e.request).then(function(response) {
return caches.open(cacheName).then(function(cache) {
cache.put(e.request, response.clone());
return response;
});
})
);
return;
}
e.respondWith(
caches
.match(e.request)
.then(function(response) {
return (
response ||
fetch(e.request).then(function(response) {
return caches.open(cacheName).then(function(cache) {
cache.put(e.request, response.clone());
return response;
});
})
);
})
.catch(function() {
return caches.match(offlinePage);
})
);
});
// https://developer.mozilla.org/en-US/docs/Web/API/Service_Worker_API/Using_Service_Workers
var CACHE_VERSION = '1.0.4';
var CACHE_NAME = CACHE_VERSION + '-sw-cache';
/*
Install is the first event sent to the service worker after registration
The worker prepares to make resources available offline (caching files)
When completed, an existing service worker may be active, in this case, the new worker will wait until
all tabs have been closed to be active
The new service worker can call skipWaiting() any time in the install phase
to be asked to be activated immediatley upon install
*/
function onInstall(event) {
// The promise that skipWaiting() returns can be safely ignored.
self.skipWaiting();
// console.log('[Serviceworker]', "Installing!", event);
event.waitUntil(
caches.open(CACHE_NAME).then(function(cache) {
return cache.addAll([
'/logo-kg.jpg',
'/offline.html',
]);
})
);
}
/*
This phase allows for cleanup of caches affected by the service worker installed
*/
function onActivate(event) {
// console.log('[Serviceworker]', "Activating!", event);
event.waitUntil(
caches.keys().then(function(cacheNames) {
return Promise.all(
cacheNames.filter(function(cacheName) {
// Return true if you want to remove this cache,
// but remember that caches are shared across
// the whole origin
return cacheName.indexOf(CACHE_VERSION) !== 0;
}).map(function(cacheName) {
return caches.delete(cacheName);
})
);
})
);
}
/*
Service workers can now access resources from the cache
Fetch event is fired every time any resource controlled by a service workeris requested
(includes documents inside the scope, resources referenced in the scope ex. cross origin requests)
intercept the request by using `event.respondWith()`
*/
// Borrowed from https://github.com/TalAter/UpUp
function onFetch(event) {
event.respondWith(
// try to return untouched request from network first, catch will receive the failed request
fetch(event.request).catch(function() {
// if it fails, try to return request from the cache
return caches.match(event.request).then(function(response) {
if (response) {
return response;
}
// if not found in cache, return default offline content for navigate requests
if (event.request.mode === 'navigate' ||
(event.request.method === 'GET' && event.request.headers.get('accept').includes('text/html'))) {
// console.log('[Serviceworker]', "Fetching offline content", event);
return caches.match('/offline.html');
}
})
})
);
}
self.addEventListener('install', onInstall);
self.addEventListener('activate', onActivate);
self.addEventListener('fetch', onFetch);