如何用ServiceWorker生命周期替换appcache生命周期事件

时间:2020-04-08 06:32:10

标签: javascript html service-worker

我正在尝试将应用程序缓存更改为应用程序中的serviceworker以进行脱机工作。从生命周期事件开始,我已经从html页面中删除了manifest标签,并创建了serviceworker.js。但是,appcache事件的用法如下:

function framework(){
    this.appCache = window.applicationCache;
  //more other codes
}
  var fw = new framework();

现在,生命周期事件的检查如下:

if (fw.appCache) {
/* Checking for an update. Always the first event fired in the sequence.*/ fw.appCache.addEventListener('checking',    handleCacheEvent, false);
/* An update was found. The browser is fetching resources.*/               fw.appCache.addEventListener('downloading', handleCacheEvent, false);
/* Fired if the manifest file returns a 404 or 410.
   This results in the application cache being deleted. */                 fw.appCache.addEventListener('obsolete',    handleCacheEvent, false);
/* The manifest returns 404 or 410, the download failed,
   or the manifest changed while the download was in progress.*/           fw.appCache.addEventListener('error',       handleCacheError, false);
/* Fired for each resource listed in the manifest as it is being fetched.*/fw.appCache.addEventListener('progress',    handleProgressEvent, false);
/*Fired after the first cache of the manifest. */                          fw.appCache.addEventListener('cached',  function(event){handleCacheEvent(event);removeProcessing();$("#processingTextId").html("");}, false);
/* Fired after the first download of the manifest.*/                       fw.appCache.addEventListener('noupdate', function(event){handleCacheEvent(event);removeProcessing(); $("#processingTextId").html("");}, false);
/* Fired when the manifest resources have been newly redownloaded. */      fw.appCache.addEventListener('updateready', function(e) {if (fw.appCache.status == fw.appCache.UPDATEREADY) {alert('Successful'); try{fw.appCache.swapCache();window.location.reload();} catch(err){}}}, false);

}

function handleCacheEvent(event) {$("#processingTextId").html(event.type);}
function handleProgressEvent(event) {$("#processingTextId").html("(" + event.loaded + " of "+ event.total +")");}
function handleCacheError(event) {$("#processingTextId").html("Cache failed to update!")

所以,我的问题是如何用服务工作者事件替换此事件。我的服务人员已注册并正确缓存资产。现在,我正在index.html

注册

<script type="text/javascript">
       if('serviceWorker' in navigator){
            navigator.serviceWorker.register('serviceworker.js')
            .then(registration =>{
                console.log('registration successful:',registration.scope);
            })
            .catch(err=>{
                console.log('registration failed:',err);
            });
    }


    </script>

我创建了单独的serviceworker.js。

如何用serviceworker替换那些appcache事件?

1 个答案:

答案 0 :(得分:1)

使用服务人员时,您不会自动遇到任何这些事件。此外,服务工作者何时填充和更新缓存的模型比AppCache的模型更“开放式”,因此并非总是可能将服务工作者缓存转换为等效的AppCache事件。

不过,总的来说,有两点可以帮助您:

阅读Service Worker Lifecycle。您可能关心的某些事件可以通过侦听服务人员生命周期的等效更改来近似。例如,如果您precache some URLs during service worker installation,则离开installing状态的新注册服务工作者将大致等同于AppCache清单完成缓存的时间。同样,如果您检测到何时有以前注册的服务工作者的更新(并且该更新是由于要预缓存的URL列表的更改而引起的),那么这大致相当于更新AppCache清单的时间。

如果您的服务人员使用“运行时”缓存,其中URL被添加到fetch处理程序中的缓存中,那么您可以使用以下技术来告诉客户页面何时已添加新项目缓存,使用postMessage()进行交流。

服务工作者的JavaScript的一部分:

const cacheAddAndNotify = async (cacheName, url) => {
  const cache = await caches.open(cacheName);
  await cache.add(url);
  const clients = await self.clients.matchAll();
  for (const client of clients) {
    client.postMessage({cacheName, url});
  }
};

self.addEventListener('fetch', (event) => {
  // Use cacheAddAndNotify() to add to your cache and notify all clients.
});

您的网络应用程序的JavaScript的一部分:

if ('serviceWorker' in navigator) {
  navigator.serviceWorker.addEventListener('message', (event) => {
    const {cacheName, url} = event.data;
    // cacheName and url represent the entry that was just cached.
  });
}

同样,您所听内容的详细信息以及您对此的反应方式实际上将完全取决于您在服务人员中所采用的逻辑。不要期望所有事件之间都存在1:1的映射。取而代之的是,利用这次迁移来思考您实际上关心的与缓存相关的更改,并专注于侦听这些更改(通过服务工作者生命周期事件或postMessage()通信)。