From 3c232e9b97d22ae9a9f987a82f77c9b157aa97b8 Mon Sep 17 00:00:00 2001 From: hzj <1304805162@qq.com> Date: Thu, 25 Dec 2025 17:06:24 +0800 Subject: [PATCH] =?UTF-8?q?feat(=E6=96=B0=E9=85=8D=E7=BD=AE=E7=B1=BB):=20?= =?UTF-8?q?=E5=9B=BE=E7=89=87=E7=BC=93=E5=AD=98=E7=89=88=E6=9C=AC=E5=8F=B7?= =?UTF-8?q?=E6=96=87=E4=BB=B6=EF=BC=8C=E7=94=A8=E4=BA=8E=E6=8E=A7=E5=88=B6?= =?UTF-8?q?=E5=9B=BE=E7=89=87=E7=BC=93=E5=AD=98=E7=9A=84=E6=B8=85=E9=99=A4?= =?UTF-8?q?=EF=BC=8C=E5=8F=96=E6=B6=88=E4=B9=8B=E5=89=8D=E5=AE=8C=E5=85=A8?= =?UTF-8?q?=E7=94=B1=E5=BA=94=E7=94=A8=E7=89=88=E6=9C=AC=E5=8F=B7=E6=8E=A7?= =?UTF-8?q?=E5=88=B6=E7=BC=93=E5=AD=98=E7=9A=84=E6=96=B9=E6=A1=88=EF=BC=8C?= =?UTF-8?q?=E4=B8=A4=E8=80=85=E7=BB=93=E5=90=88=EF=BC=8C=E7=8E=B0=E5=9C=A8?= =?UTF-8?q?=E5=BA=94=E7=94=A8=E5=8F=B7=E5=8F=AA=E6=9C=89=E5=9C=A8=E5=A4=A7?= =?UTF-8?q?=E6=9B=B4=E6=96=B0=E6=97=B6=E6=89=8D=E4=BC=9A=E6=B8=85=E9=99=A4?= =?UTF-8?q?=E7=BC=93=E5=AD=98=EF=BC=8C=E5=85=B6=E4=BB=96=E6=83=85=E5=86=B5?= =?UTF-8?q?=E7=94=B1=E7=BC=93=E5=AD=98=E7=89=88=E6=9C=AC=E5=8F=B7=E6=8E=A7?= =?UTF-8?q?=E5=88=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/config/imageCacheVersion.js | 18 +++++ src/main.js | 1 + src/utils/imageCacheManager.js | 128 ++++++++++++++++++++++++++++---- src/utils/versionChecker.js | 19 +++-- 4 files changed, 143 insertions(+), 23 deletions(-) create mode 100644 src/config/imageCacheVersion.js diff --git a/src/config/imageCacheVersion.js b/src/config/imageCacheVersion.js new file mode 100644 index 0000000..e740407 --- /dev/null +++ b/src/config/imageCacheVersion.js @@ -0,0 +1,18 @@ +// src/config/imageCacheVersion.js +// 图片缓存版本号配置 +export const IMAGE_CACHE_VERSION = { + // 图片缓存版本号,仅在图片资源有重大变化时更新 + version: '1.0.0', // 可以根据需要更新此版本号 + + // 缓存类型控制:'images'、'assets' 或 'all' + // 'images': 只清除图片缓存 (likei-images-v) + // 'assets': 只清除资产缓存 (likei-assets-v) + // 'all': 清除所有缓存 + cacheType: 'all', // 默认清除所有缓存,可根据需要修改 + + // 版本更新说明(用于记录更新原因) + updateReason: 'Initial image cache version for major release', + + // 更新时间戳 + updateTime: new Date().toISOString(), +} diff --git a/src/main.js b/src/main.js index 17a4cdb..b5f8e43 100644 --- a/src/main.js +++ b/src/main.js @@ -1,3 +1,4 @@ +// src/main.js import './assets/main.css' import { logEnvInfo } from './utils/env.js' import { versionChecker } from './utils/versionChecker.js' diff --git a/src/utils/imageCacheManager.js b/src/utils/imageCacheManager.js index c846683..f29f97c 100644 --- a/src/utils/imageCacheManager.js +++ b/src/utils/imageCacheManager.js @@ -1,11 +1,15 @@ // src/utils/imageCacheManager.js +import { IMAGE_CACHE_VERSION } from '@/config/imageCacheVersion' + class ImageCacheManager { constructor() { - this.cacheVersionKey = 'likei-image-cache-version' + this.cacheVersionKey = 'h5_app_version' this.currentAppVersion = import.meta.env.VITE_APP_VERSION || '1.0.0' + this.currentImageVersion = IMAGE_CACHE_VERSION.version // 使用完整版本号 + this.versionType = import.meta.env.VITE_VERSION_TYPE || 'patch' // major, minor, patch - this.imageCacheName = `likei-images-v${this.currentAppVersion}` // OSS图片 - this.assetCacheName = `likei-assets-v${this.currentAppVersion}` // 本地assets + this.imageCacheName = `likei-images-v${this.currentImageVersion}` // OSS图片 + this.assetCacheName = `likei-assets-v${this.currentImageVersion}` // 本地assets this.maxCacheItems = 100 // 最大缓存数量(100张) this.maxCacheSize = 100 * 1024 * 1024 // 最大缓存大小(100MB) @@ -15,6 +19,23 @@ class ImageCacheManager { this.init() } + // 解析版本号为数组 [major, minor, patch] + parseVersion(version) { + return version.split('.').map(Number) + } + + // 比较两个版本号,返回是否版本发生了变化(任何部分的变化) + isVersionChanged(cachedVersion, currentVersion) { + return cachedVersion !== currentVersion + } + + // 检查是否是major版本更新 + isMajorVersionUpdate(cachedVersion, currentVersion) { + const [cachedMajor] = this.parseVersion(cachedVersion) + const [currentMajor] = this.parseVersion(currentVersion) + return currentMajor > cachedMajor + } + async getCacheForUrl(url) { // 规范化 URL const normalizedUrl = this.normalizeUrl(url) @@ -80,15 +101,62 @@ class ImageCacheManager { // 版本检查逻辑 async checkVersionAndUpdate() { const cachedVersion = localStorage.getItem(this.cacheVersionKey) + const cachedImageVersion = localStorage.getItem('likei-image-version') if (!cachedVersion) { + // 首次安装:保存当前版本和图片版本 localStorage.setItem(this.cacheVersionKey, this.currentAppVersion) + localStorage.setItem('likei-image-version', IMAGE_CACHE_VERSION.version) return } - if (cachedVersion !== this.currentAppVersion) { - await this.clearOldCaches() - localStorage.setItem(this.cacheVersionKey, this.currentAppVersion) + // 检查是否是major版本更新 + const isMajorUpdate = this.isMajorVersionUpdate(cachedVersion, this.currentAppVersion) + + if (isMajorUpdate) { + // major版本更新:清除所有缓存 + console.log( + `检测到major版本更新,从 ${cachedVersion} 更新到 ${this.currentAppVersion},清除所有缓存` + ) + await this.clearAllCaches() + } else { + // 非major版本更新:检查图片版本是否变化 + const isImageVersionChanged = this.isVersionChanged( + cachedImageVersion || '1.0.0', + IMAGE_CACHE_VERSION.version + ) + + if (isImageVersionChanged) { + // 图片版本变化:根据配置清除指定类型的缓存 + console.log( + `检测到图片版本变化,从 ${cachedImageVersion} 更新到 ${IMAGE_CACHE_VERSION.version},根据配置清除缓存类型: ${IMAGE_CACHE_VERSION.cacheType}` + ) + await this.clearCacheByType(IMAGE_CACHE_VERSION.cacheType) + } + // 如果图片版本未变化且不是major更新,则不执行任何清除操作 + } + + // 更新版本号 + localStorage.setItem(this.cacheVersionKey, this.currentAppVersion) + localStorage.setItem('likei-image-version', IMAGE_CACHE_VERSION.version) + } + + // 根据类型清除缓存 + async clearCacheByType(cacheType) { + switch (cacheType) { + case 'images': + await this.clearOldImageCaches() + break + case 'assets': + await this.clearOldAssetCaches() + break + case 'all': + await this.clearAllCaches() + break + default: + // 默认只清除图片缓存 + await this.clearOldImageCaches() + break } } @@ -180,25 +248,59 @@ class ImageCacheManager { } } - // 清除全部旧图片缓存 - async clearOldCaches() { + // 清除全部旧图片缓存(仅在图片版本更新时调用) + async clearOldImageCaches() { if (!('caches' in window)) return try { const cacheNames = await caches.keys() - const oldCaches = cacheNames.filter( + const oldImageCaches = cacheNames.filter( (name) => - (name.startsWith('likei-images-v') || name.startsWith('likei-assets-v')) && - name !== this.imageCacheName && - name !== this.assetCacheName + name.startsWith('likei-images-v') && !name.includes(`v${this.currentImageVersion}`) // 排除当前版本的缓存 ) - await Promise.all(oldCaches.map((name) => caches.delete(name))) + console.log('正在清除旧图片缓存:', oldImageCaches) + await Promise.all(oldImageCaches.map((name) => caches.delete(name))) } catch (error) { console.warn('清理旧图片缓存失败:', error) } } + // 清除全部旧资产缓存(仅在图片版本更新时调用) + async clearOldAssetCaches() { + if (!('caches' in window)) return + + try { + const cacheNames = await caches.keys() + const oldAssetCaches = cacheNames.filter( + (name) => + name.startsWith('likei-assets-v') && !name.includes(`v${this.currentImageVersion}`) // 排除当前版本的缓存 + ) + + console.log('正在清除旧资产缓存:', oldAssetCaches) + await Promise.all(oldAssetCaches.map((name) => caches.delete(name))) + } catch (error) { + console.warn('清理旧资产缓存失败:', error) + } + } + + // 清除所有缓存(仅在major版本更新时调用) + async clearAllCaches() { + if (!('caches' in window)) return + + try { + const cacheNames = await caches.keys() + const allCaches = cacheNames.filter( + (name) => name.startsWith('likei-images-v') || name.startsWith('likei-assets-v') + ) + + console.log('正在清除所有缓存:', allCaches) + await Promise.all(allCaches.map((name) => caches.delete(name))) + } catch (error) { + console.warn('清理所有缓存失败:', error) + } + } + // 判断是否为适合缓存资源 isBuildAsset(url) { try { diff --git a/src/utils/versionChecker.js b/src/utils/versionChecker.js index 2e9abd9..6e9c47d 100644 --- a/src/utils/versionChecker.js +++ b/src/utils/versionChecker.js @@ -1,3 +1,4 @@ +// src/utils/versionChecker.js // 版本检查工具 import { imageCacheManager } from '@/utils/imageCacheManager' @@ -71,8 +72,7 @@ export class VersionChecker { const versionResult = await this.checkServerVersion() if (versionResult.shouldUpdate) { - this.handleVersionUpdate() - localStorage.setItem('likei-image-cache-version', this.currentVersion) // 同步 imageCacheManager 的版本信息 + await this.handleVersionUpdate(versionResult.versionType) return true } @@ -82,7 +82,6 @@ export class VersionChecker { if (storedLocalVersion !== this.currentVersion) { // 本地版本变化,可能是首次加载或本地版本升级 localStorage.setItem(this.storageKey, this.currentVersion) - localStorage.setItem('likei-image-cache-version', this.currentVersion) console.log(`本地版本更新到: ${this.currentVersion}`) } @@ -96,15 +95,16 @@ export class VersionChecker { // 根据更新类型决定清除策略 switch (updateType) { case 'major': - await this.clearCache() // 重大更新:清除所有缓存 + // 重大更新:清除所有缓存(不管图片版本号是否更新) + await this.clearCache() break case 'minor': - await imageCacheManager.clearCacheSelective('all') // 一般更新:清除图片和assets缓存 - this.clearSessionData() // 清除 session 数据 - break case 'patch': - // 日常小更新:清除缓存 - await imageCacheManager.clearCacheSelective('all') // 小更新:清除图片和assets缓存 + // minor或patch更新:检查图片版本号是否更新 + // 如果图片版本号更新,则按imageCacheVersion中的cacheType清除缓存 + // 如果图片版本号未更新,则不做任何缓存清除处理 + await imageCacheManager.checkVersionAndUpdate() + this.clearSessionData() // 清除 session 数据 break default: // 默认:清除所有缓存 @@ -113,7 +113,6 @@ export class VersionChecker { localStorage.setItem(this.storageKey, this.currentVersion) localStorage.setItem(this.serverVersionKey, this.currentVersion) - localStorage.setItem('likei-image-cache-version', this.currentVersion) // 直接刷新页面 this.forceReload()