You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Workbox配置Service Worker时离线触发'__jstcache'读取错误

问题

我使用Workbox模块处理Service Worker文件,代码如下:

importScripts('https://storage.googleapis.com/workbox-cdn/releases/6.4.1/workbox-sw.js');

const { routing, strategies, cacheableResponse, expiration, recipes } = workbox;
const { registerRoute } = routing;
const {offlineFallback} = recipes;
const {ExpirationPlugin} = expiration;
const { StaleWhileRevalidate } = strategies;
const { CacheableResponsePlugin } = cacheableResponse;


self.__WB_MANIFEST;
registerRoute(
  ({ request }) => request.destination === 'script', // 仅匹配目标为script的请求
  new StaleWhileRevalidate({
    cacheName: 'js-cache', // 缓存名称
    plugins: [
      new CacheableResponsePlugin({ statuses: [0, 200] }), // 仅缓存状态码为0或200的响应
      new ExpirationPlugin({
         // 缓存有效期为一周
         maxAgeSeconds: 7 * 24 * 60 * 60,
      
      })
    ],
  })
);
workbox.routing.setCatchHandler(({ event }) => {
    if (event.request.destination === 'document') {
      return caches.match('/offline.html');
    }
    return Response.error();
  });

期望实现离线时提供缓存文件,但切换到离线模式后立即崩溃,抛出错误:Cannot read properties of null (reading '__jstcache'),错误截图显示该报错信息。

解决方案

这个错误核心原因是offline.html未被提前缓存,离线时caches.match('/offline.html')返回null,后续代码尝试访问null的属性导致崩溃。另外你的代码存在两个关键问题:一是self.__WB_MANIFEST仅被引用但未用于预缓存资源;二是导入了offlineFallback但未实际使用。

以下是修复后的代码:

importScripts('https://storage.googleapis.com/workbox-cdn/releases/6.4.1/workbox-sw.js');

const { routing, strategies, cacheableResponse, expiration, precaching, recipes } = workbox;
const { registerRoute } = routing;
const { offlineFallback } = recipes;
const { ExpirationPlugin } = expiration;
const { StaleWhileRevalidate } = strategies;
const { CacheableResponsePlugin } = cacheableResponse;

// 预缓存清单中的资源,需确保offline.html在构建生成的清单内
precaching.precacheAndRoute(self.__WB_MANIFEST);

// 若构建工具未自动将offline.html加入清单,可手动添加
// precaching.precacheAndRoute([
//   ...self.__WB_MANIFEST,
//   { url: '/offline.html', revision: '123' }
// ]);

// 缓存JS资源的路由规则
registerRoute(
  ({ request }) => request.destination === 'script',
  new StaleWhileRevalidate({
    cacheName: 'js-cache',
    plugins: [
      new CacheableResponsePlugin({ statuses: [0, 200] }),
      new ExpirationPlugin({
        maxAgeSeconds: 7 * 24 * 60 * 60,
      })
    ],
  })
);

// 使用Workbox内置的离线回退方案,自动处理页面离线访问
offlineFallback({
  pageFallback: '/offline.html',
});

关键改动说明

  • 启用预缓存:调用precaching.precacheAndRoute(self.__WB_MANIFEST),这会将构建工具生成的资源清单(包含offline.html)提前缓存,确保离线时能获取到。如果构建工具未自动包含offline.html,可以手动添加到预缓存列表。
  • 使用offlineFallback recipe:Workbox内置的该方案会自动处理离线回退逻辑,比手动编写setCatchHandler更可靠,它会确保指定的pageFallback文件被正确缓存。
  • 可选:手动处理回退(不推荐):如果坚持手动写setCatchHandler,需要添加await并判断缓存结果是否为null,避免直接访问null的属性:
workbox.routing.setCatchHandler(async ({ event }) => {
  if (event.request.destination === 'document') {
    const cachedPage = await caches.match('/offline.html');
    return cachedPage || Response.error();
  }
  return Response.error();
});

内容的提问来源于stack exchange,提问作者Danilo Kujacic

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 04:01:16