javascript - 仅在 Chrome 中(服务 worker ): '... a redirected response was used for a request whose redirect mode is not "follow"'

标签 javascript google-chrome service-worker fetch-api

当我在 Chrome 中刷新(或离线)时,我得到“无法访问此站点”并且以下内容记录到控制台:The FetchEvent for "http://localhost:8111/survey/174/deployment/193/answer/offline/attendee/240/”导致网络错误响应:重定向响应用于重定向模式不是“跟随”的请求。。当我在 Firefox 中刷新时,一切正常。有人可以解释为什么会这样吗?

这是我简化的软件。

importScripts("/static/js/libs/idb.js")

var CACHE_NAME = "upshot-cache-version3"
var urlsToCache = [...]

self.addEventListener("install", event => {
  event.waitUntil(
    caches
      .open(CACHE_NAME)
      .then(cache => {
        urlsToCache.map(url => cache.add(url))
      })
  )
})

self.addEventListener("activate", event => {
  clients.claim()
})

self.addEventListener('fetch', event => {
  event.respondWith(
    caches
      .match(event.request)
      .then(response => {

        if (response) {
          return response
        }

        var fetchRequest = event.request.clone()

        return fetch(fetchRequest).then(response => {
          if (!response || response.status !== 200 || response.type !== 'basic') {
            return response
          }
          var responseToCache = response.clone()
          caches.open(CACHE_NAME).then(cache => cache.put(event.request, responseToCache))
          return response
        })

      })
  )
})

最佳答案

这是由于(相对)最近关于可以使用什么样的响应来满足导航的安全限制发生了变化。它应该适用于所有支持服务 worker 的浏览器(即今天的 Chrome 和 Firefox),但您可能正在使用过时的 Firefox 版本进行测试。

可以在 issue tracker entry 中找到有关更改内容的背景信息, 还有 more background关于导致基础规范的决定。

在修改您的服务 worker 以处理安全限制方面,如果您当前正在使用 HTTP 30x 重定向到不同的 URL 来响应对某些 URL 的导航请求,您需要注意不要只存储那个直接在缓存中重定向响应。

您可以通过检查 response.redirected 是否为 true 来判断给定的响应是否被重定向,如果是,则使用类似的代码(改编自Workbox 项目)来创建响应的“干净”副本,然后可以将其存储在缓存中:

function cleanResponse(response) {
  const clonedResponse = response.clone();

  // Not all browsers support the Response.body stream, so fall back to reading
  // the entire body into memory as a blob.
  const bodyPromise = 'body' in clonedResponse ?
    Promise.resolve(clonedResponse.body) :
    clonedResponse.blob();

  return bodyPromise.then((body) => {
    // new Response() is happy when passed either a stream or a Blob.
    return new Response(body, {
      headers: clonedResponse.headers,
      status: clonedResponse.status,
      statusText: clonedResponse.statusText,
    });
  });
}

关于javascript - 仅在 Chrome 中(服务 worker ): '... a redirected response was used for a request whose redirect mode is not "follow"',我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45434470/

相关文章:

javascript - 刷新带有 <script> 标签的 div

javascript - 通过 Angular 2/Ionic 2 中的构造函数刷新数据

javascript - Puppeteer.launch 取决于操作系统

函数(构造函数)返回类型中的 Javascript 奇怪行为

html - 防止在 iframe 中导航更改父站点历史记录

google-chrome - 如何在 Manifest_version 3 Chrome 扩展程序中将内容复制到剪贴板?

javascript - 努力理解为什么我的服务人员不工作 - 未捕获( promise )TypeError : Request failed

reactjs - 如何在 Service Worker 中使用 ApplicationInsights-JS?

javascript - 在 CalendarDateInterval 控件中突出显示开始日期

javascript - Ping 服务工作线程而不显示通知