Angular Service Worker是否会清理旧版本缓存?关于PWA缓存持续增长的技术问询
Angular Service Worker 旧版本缓存清理问题解答
默认缓存清理逻辑说明
先给你明确答案:Angular PWA 原理图默认不会自动添加主动清理旧版本缓存的代码。不过这并不代表它没有可扩展性,只是默认的 Service Worker 行为更偏向保守——它会保留旧版本缓存一段时间,用来支持「新版本加载失败时回退到旧版本」的降级策略,但不会在新版本发布后立刻删除旧缓存,这就是你看到缓存体积持续翻倍的核心原因。
为什么缓存会持续增长?
当你发布新版本时,Angular Service Worker 会对比新旧版本的资源哈希列表,下载并缓存新版本的所有资源,但旧版本的缓存只会被标记为「过时」,并不会立即被删除。默认的清理触发时机比较晚,不会在新版本刚激活就清理旧缓存,所以反复发布版本时,缓存就会不断累积。
解决缓存持续增长的两种方案
方案一:通过配置自动限制缓存数量/有效期
你可以直接修改 ngsw-config.json,给缓存设置版本数量上限或过期时间,让旧缓存自动被清理,无需编写额外代码:
{ "index": "/index.html", "assetGroups": [ { "name": "app", "installMode": "prefetch", "cacheConfig": { "maxSize": 3, // 最多保留3个版本的缓存 "maxAge": "2d", // 缓存最长保留2天 "timeout": "10s" }, "resources": { "files": [ "/favicon.ico", "/index.html", "/manifest.webmanifest", "/*.css", "/*.js" ] } }, { "name": "assets", "installMode": "lazy", "updateMode": "prefetch", "cacheConfig": { "maxSize": 5, "maxAge": "7d" }, "resources": { "files": [ "/assets/**", "/*.(svg|cur|jpg|jpeg|png|apng|webp|avif|gif|otf|ttf|woff|woff2)" ] } } ] }
这种方式保留了 Angular Service Worker 自带的降级容错能力,同时避免了缓存无限增长。
方案二:自定义 Service Worker 实现激活后立即清理旧缓存
如果你希望新版本激活后立刻删除所有旧缓存(适合稳定性极高的发布场景),可以通过自定义 Service Worker 扩展实现:
- 在项目根目录创建
custom-sw.ts文件:
import { setupWorker } from '@angular/service-worker'; setupWorker('/ngsw-worker.js').then(worker => { // 监听 Service Worker 激活事件 worker.addEventListener('activate', (event) => { event.waitUntil( // 获取所有缓存名称 caches.keys().then(cacheNames => { return Promise.all( // 过滤并删除 Angular 管理的旧版本缓存 cacheNames.filter(cacheName => { // Angular 缓存名称格式为 ngsw:cache:<版本哈希>,我们只保留当前激活版本的缓存 const currentCachePrefix = 'ngsw:cache:'; return cacheName.startsWith(currentCachePrefix) && !cacheName.includes(worker.controller?.scriptURL.split('/').pop() || ''); }).map(cacheName => caches.delete(cacheName)) ); }).then(() => { // 强制所有客户端切换到新版本 Service Worker return self.clients.claim(); }) ); }); });
- 修改
angular.json配置,指定自定义 Service Worker 文件:
"projects": { "my-pwa-app": { "architect": { "build": { "options": { "serviceWorker": true, "ngswConfigPath": "src/ngsw-config.json", "assets": [ "src/favicon.ico", "src/assets", "src/manifest.webmanifest", "src/custom-sw.ts" ] } } } } }
额外提醒
默认保留旧缓存的逻辑其实是为了容错——如果新版本资源加载失败,用户可以无缝回退到旧版本。如果你选择立即清理旧缓存,一定要确保新版本的发布是稳定的,避免出现用户无法访问应用的情况。
内容的提问来源于stack exchange,提问作者Rusty
相关产品推荐
相关产品推荐

