2016-07-14 5 views
1

Ich habe den folgenden Code für einen Servicemitarbeiter:Service-Arbeiter grundlegende Setup

'use strict'; 

// Incrementing CACHE_VERSION will kick off the install event and force previously cached 
// resources to be cached again. 
const CACHE_VERSION = 1; 
let CURRENT_CACHES = { 
    offline: 'offline-v' + CACHE_VERSION 
}; 
const OFFLINE_URL = 'offline.php'; 

function createCacheBustedRequest(url) { 
    let request = new Request(url, {cache: 'reload'}); 
    // See https://fetch.spec.whatwg.org/#concept-request-mode 
    // This is not yet supported in Chrome as of M48, so we need to explicitly check to see 
    // if the cache: 'reload' option had any effect. 
    if ('cache' in request) { 
     return request; 
    } 

    // If {cache: 'reload'} didn't have any effect, append a cache-busting URL parameter instead. 
    let bustedUrl = new URL(url, self.location.href); 
    bustedUrl.search += (bustedUrl.search ? '&' : '') + 'cachebust=' + Date.now(); 
    return new Request(bustedUrl); 
} 

self.addEventListener('install', event => { 
    event.waitUntil(
     // We can't use cache.add() here, since we want OFFLINE_URL to be the cache key, but 
     // the actual URL we end up requesting might include a cache-busting parameter. 
     fetch(createCacheBustedRequest(OFFLINE_URL)).then(function(response) { 
      return caches.open(CURRENT_CACHES.offline).then(function(cache) { 
       return cache.put(OFFLINE_URL, response); 
      }); 
     }) 
    ); 
}); 

self.addEventListener('activate', event => { 
    // Delete all caches that aren't named in CURRENT_CACHES. 
    // While there is only one cache in this example, the same logic will handle the case where 
    // there are multiple versioned caches. 
    let expectedCacheNames = Object.keys(CURRENT_CACHES).map(function(key) { 
     return CURRENT_CACHES[key]; 
    }); 

event.waitUntil(
    caches.keys().then(cacheNames => { 
     return Promise.all(
      cacheNames.map(cacheName => { 
       if (expectedCacheNames.indexOf(cacheName) === -1) { 
    // If this cache name isn't present in the array of "expected" cache names, 
    // then delete it. 
    console.log('Deleting out of date cache:', cacheName); 
    return caches.delete(cacheName); 
} 
}) 
); 
}) 
); 
}); 

self.addEventListener('fetch', event => { 
    // We only want to call event.respondWith() if this is a navigation request 
    // for an HTML page. 
    // request.mode of 'navigate' is unfortunately not supported in Chrome 
    // versions older than 49, so we need to include a less precise fallback, 
    // which checks for a GET request with an Accept: text/html header. 
    if (event.request.mode === 'navigate' || 
     (event.request.method === 'GET' && 
      event.request.headers.get('accept').includes('text/html'))) { 
    console.log('Handling fetch event for', event.request.url); 
    event.respondWith(
     fetch(createCacheBustedRequest(event.request.url)).catch(error => { 
      // The catch is only triggered if fetch() throws an exception, which will most likely 
      // happen due to the server being unreachable. 
      // If fetch() returns a valid HTTP response with an response code in the 4xx or 5xx 
      // range, the catch() will NOT be called. If you need custom handling for 4xx or 5xx 
      // errors, see https://github.com/GoogleChrome/samples/tree/gh-pages/service-worker/fallback-response 
      console.log('Fetch failed; returning offline page instead.', error); 
    return caches.match(OFFLINE_URL); 
}) 
); 
} 

// If our if() condition is false, then this fetch handler won't intercept the request. 
// If there are any other fetch handlers registered, they will get a chance to call 
// event.respondWith(). If no fetch handlers call event.respondWith(), the request will be 
// handled by the browser as if there were no service worker involvement. 
}); 

Wie konnte es möglich sein, sie in einer Art und Weise zu machen, so dass es nichts auf Cache speichern hat? Die betreffende Webanwendung benötigt jederzeit eine Verbindung. Der Hauptzweck dieses Service-Mitarbeiters besteht daher darin, sich für die Telefoninstallation zu qualifizieren und später über Push-Benachrichtigungen zu verfügen.

+0

Sie können nicht nur, wissen Sie, entfernen Sie die Zeilen, in denen Sie speichern es im Cache ? –

+0

Das Problem ist, dass diese ersten Zeilen Variablen haben, die im gesamten Code verwendet werden, also habe ich mich gefragt, was das grundlegende Minimum wäre, das später noch für die Entwicklung von Push-Benachrichtigungen geeignet wäre. – Tuntex

+0

'cache.put (OFFLINE_URL, Antwort);' Das spart Dinge im Cache. Experimentieren Sie mit dem Entfernen. –

Antwort

0

Nach einigen Online-Forschung, hier ist die beste Lösung:

sw_install.js

console.log('Started', self); 
self.addEventListener('install', function(event) { 
    self.skipWaiting(); 
    console.log('Installed', event); 
}); 
self.addEventListener('activate', function(event) { 
    console.log('Activated', event); 
}); 
self.addEventListener('push', function(event) { 
    console.log('Push message received', event); 
    // TODO 
}); 

main.js

if ('serviceWorker' in navigator) { 
    console.log('Service Worker is supported'); 
    navigator.serviceWorker.register('sw_install.js').then(function(reg){ 
     console.log(':^)', reg); 
     // TODO 
    }).catch(function(err) { 
     console.log(':^(', err); 
    }); 
} 
0

können Sie verwenden npm sw-Toolbox Bibliothek (https://www.npmjs.com/package/sw-toolbox) .

main.js

if (navigator.serviceWorker){ 
    navigator.serviceWorker.register('/service-worker.js', {scope: './'}) 
     .then(function (registration) { 
      console.log("sw registered",registration); 
     }) 
     .catch(function (e) { 
      console.error("error",e); 
     }) 
    } else { 
     console.log('Service Worker is not supported in this browser.') 
    } 
} 

Service-worker.js

(global => { 
    'use strict'; 
    // Load the sw-tookbox library. 
    importScripts('/js/sw-toolbox.js'); 

    var precache_urls = [ 
     '/index.html', 
     '/img/logo.png', 
     '/img/main.png' 
    ]; 

    //for debugging only 
    global.toolbox.options.debug = true; 

    global.toolbox.router.get('/img/(.*)', self.toolbox.cacheFirst, { 
    cache: { 
    name: "Images", 
    maxEntries: 10 
    } 
    }); 
    global.toolbox.router.default = global.toolbox.networkFirst; 

    global.addEventListener('install', event => event.waitUntil(global.skipWaiting())); 
    global.addEventListener('activate', event => event.waitUntil(global.clients.claim())); 
    global.addEventListener('push', event => { 
    var pushObj = event.data.json(); 
    var pushData = pushObj.data; 

    // push payload if there, if not make an ajax get call to get it (can use fetch) 
    var title = pushData && pushData.title; 
    var body = pushData && pushData.body; 
    var icon = '/img/logo.png'; 
       event.waitUntil(global.registration.showNotification(title, { 
       body: body, 
       icon: icon, 
       badge: icon 
       data:pushData 
      })); 

     }); 
    global.addEventListener('notificationclick', event => { 
    event.notification.close(); 
    var url = event.notification.data.url|| '/'; 
    event.waitUntil(
     clients.matchAll({ 
     type: 'window' 
     }).then(windowClients => { 
     console.log('WindowClients', windowClients); 
     for (var i = 0; i < windowClients.length; i++) { 
      var client = windowClients[i]; 
      console.log('WindowClient', client); 
      if (client.url === url && 'focus' in client) { 
      return client.focus(); 
      } 
     } 
     if (clients.openWindow) { 
     return clients.openWindow(url); 
     } 
    })); 
    }); 
})(self);