如何卸载服务工作者?

时间:2015-11-14 03:28:31

标签: html5 google-chrome service-worker

从我的根目录中删除/serviceworker.js后,Chrome仍会运行我从我的webroot中删除的服务工作者。如何从我的网站和Chrome中卸载服务工作者,以便我可以重新登录我的网站?

我已将问题跟踪到Service Work的缓存机制,我只想暂时删除,直到我有时间调试它。我使用的登录脚本会重定向到Google的服务器,以便他们登录自己的Google帐户。但是我从login.php页面得到的只是ERR_FAILED消息。

15 个答案:

答案 0 :(得分:240)

您可以通过以下方式以编程方式删除服务工作者:

navigator.serviceWorker.getRegistrations().then(function(registrations) {
 for(let registration of registrations) {
  registration.unregister()
} })

文档:getRegistrationsunregister

您还可以在Chrome Devtools的“应用程序”标签下删除服务工作者。

答案 1 :(得分:84)

您还可以转到以下网址: chrome:// serviceworker-internals / ,然后从那里取消注册服务工作。

答案 2 :(得分:22)

在Google Chrome中,您可以转到开发者工具(F12) - >申请 - >服务工作人员从该列表中取消注册特定域名。

Screenshot

此方法在网站的开发模式中有效,并且大部分都在localhost上运行,这是您可能需要进行其他项目的开发。

答案 3 :(得分:4)

您应该在设备中检测到两个API:getRegistrationsgetRegistration。服务工作者在所有平台中都没有唯一的API集。例如,某些浏览器只有navigator.serviceWorker.getRegistration,没有navigator.serviceWorker.getRegistrations。所以你应该考虑两者。

答案 4 :(得分:1)

仅供参考,如果您使用的是MacOS Safari 浏览器,则有一种方法可以强制注销服务工作者(Safari 12.1的步骤和图像):

  1. Safari>首选项...>隐私>管理网站数据… Safari Preferences : Privacy

  2. 输入域名(例如“ localhost”),然后单击“删除” Safari Preferences : Privacy : manage website data

注意:除了服务工作者外,这还将删除该域的所有缓存,cookie和数据库。

答案 5 :(得分:1)

检测服务人员:

navigator.serviceWorker.controller

删除服务人员的代码:

navigator.serviceWorker.getRegistrations()
  .then(registrations => {
    registrations.forEach(registration => {
      registration.unregister();
    })
  });

  navigator.serviceWorker.getRegistrations().then(function(registrations) {
   for(let registration of registrations) {
    registration.unregister()
  } })

  if(window.navigator && navigator.serviceWorker) {
    navigator.serviceWorker.getRegistrations()
    .then(function(registrations) {
      for(let registration of registrations) {
        registration.unregister();
      }
    });
  }

  if ('caches' in window) {
      caches.keys()
        .then(function(keyList) {
            return Promise.all(keyList.map(function(key) {
                return caches.delete(key);
            }));
        })
  }

  if ('serviceWorker' in navigator) {
        navigator.serviceWorker.getRegistrations().then(function (registrations) {
          for (const registration of registrations) {
            // unregister service worker
            console.log('serviceWorker unregistered');
            registration.unregister();

            setTimeout(function(){
              console.log('trying redirect do');
              window.location.replace(window.location.href); // because without redirecting, first time on page load: still service worker will be available
            }, 3000);
          }
        });
      }

答案 6 :(得分:1)

此代码与Internet Explorer兼容:

if (navigator.serviceWorker) {
    navigator.serviceWorker.getRegistrations().then(                
        function(registrations) {
            for (let idx in registrations) {
                registrations[idx].unregister()
            }
        })
}

IE不支持'for ... of'和'for ... of'的构造可能导致“'SCRIPT1004:预期的';'”错误

答案 7 :(得分:1)

也可以通过Chrome在“应用程序”标签中完成此操作: enter image description here

答案 8 :(得分:1)

对我来说,我只是用一个新的不存在的范围服务工作者来代替旧的,

ServiceWorker: {
        events: true,
        // what range of URLs a service worker can control. Use a nonexistent path to disable ServiceWorker
        scope: '/disable-service-worker/',
      },

至于 app.js,我添加以下代码来注销旧的 sw:

if ('serviceWorker' in navigator) {
  navigator.serviceWorker.getRegistrations().then(registrations => {
    for (const registration of registrations) {
      // keep only serviceWorker which scope is /disable-service-worker/, The purpose is to make serviceWorker useless
      if (registration.scope.includes('/disable-service-worker/') === false) {
        registration.unregister()
      }
    }
  });
  // clear cache of service worker
  caches.keys().then(keyList => {
    return Promise.all(
      keyList.map(key => {
        return caches.delete(key);
      }),
    );
  });
}

答案 9 :(得分:0)

除了给出的正确答案外,如果您还想删除软件缓存,可以使用:

@Bean
TaskSchedulerCustomizer taskSchedulerCustomizer() {
    return taskScheduler -> {
        taskScheduler.setAwaitTerminationSeconds(60);
        taskScheduler.setWaitForTasksToCompleteOnShutdown(true);
    };
}

您可以阅读more here(段落:“取消服务人员注册”)

或通过浏览器访问“缓存存储”部分,然后单击“清除站点数据”按钮:

enter image description here

答案 10 :(得分:0)

安全卸载Service Worker

if ('serviceWorker' in navigator) {
      navigator.serviceWorker.getRegistrations().then(function (registrations) {
        for (const registration of registrations) {
          // unregister service worker
          console.log('serviceWorker unregistered');
          registration.unregister();
        }
      });
    }

答案 11 :(得分:0)

其他答案都将代码添加到实时网站中,以删除服务人员。但是,我不想让实时代码永远运行,所以我开发了一种可以在服务工作者内部运行的解决方案。步骤如下,我在my blog上发布了更多详细信息和说明。

  1. 删除注册服务工作者的代码。
  2. 用以下文件替换服务工作者脚本。新代码必须可以从以前的服务工作者使用的相同URL获得。如果您过去有多个Service Worker URL,则应在所有URL上重复代码。
console.log("Cleanup Service Worker Starting");

caches.keys()
    .then(keys =>
        Promise.all(
            keys.map(async key => console.log("caches.delete", key, await caches.delete(key)))))
    .then(async () => {
        console.log("registration.unregister", await registration.unregister());
    })
    .then(() => console.log("DONE"))
    .catch(console.error);

此代码相当简单。首先,它删除所有缓存,然后注销自身。

用户的浏览器将自动检查更新的服务人员the next time they load your website, or the next event 24h after the last service worker check。这意味着现有用户将在下次访问时运行此清理。

答案 12 :(得分:0)

打开此页面: chrome:// serviceworker-internals ,然后单击取消注册按钮

如果要注销所有服务人员,请打开开发人员工具并在上一页上运行此代码。

document.querySelectorAll("button.unregister").forEach(item=>{ item.click()})

答案 13 :(得分:0)

如果您的服务人员不允许您更新文件。您将需要使用以下代码替换serviceworker文件(sw.js / ServiceWorker.js):

self.addEventListener('install', function(e) {
  self.skipWaiting();
});

self.addEventListener('activate', function(e) {
  self.registration.unregister()
    .then(function() {
      return self.clients.matchAll();
    })
    .then(function(clients) {
      clients.forEach(client => client.navigate(client.url))
    });
});

Source here

答案 14 :(得分:0)

在 Chrome 中打开

chrome://serviceworker-internals/?devtools

然后在控制台中 F12

$$('.unregister').forEach(b => b.click())