From a56fe64200c36abf35a0351952f2e9badaa9fd84 Mon Sep 17 00:00:00 2001 From: Victor_Jay Date: Sun, 31 May 2026 02:16:54 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E4=BF=AE=E5=A4=8D=E9=9D=99=E6=80=81?= =?UTF-8?q?=E8=B5=84=E6=BA=90=E5=93=88=E5=B8=8C=20key=20=E4=B8=8E=E6=A8=A1?= =?UTF-8?q?=E6=9D=BF=20URL=20=E8=B7=AF=E5=BE=84=E4=B8=8D=E5=8C=B9=E9=85=8D?= =?UTF-8?q?=E5=AF=BC=E8=87=B4=E7=89=88=E6=9C=AC=E5=8F=B7=E5=85=A8=E4=B8=BA?= =?UTF-8?q?=200?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 重构 walkStaticDir 统一处理三个 static 目录 - URL key 基于文件相对于 static 目录的路径,不含主题目录名 - 哈希算法从 SHA-1 改为 CRC32(更快更匹配场景) --- internal/common/helper.go | 102 ++++++++++++-------------------------- 1 file changed, 32 insertions(+), 70 deletions(-) diff --git a/internal/common/helper.go b/internal/common/helper.go index 35d55ee..8be8312 100644 --- a/internal/common/helper.go +++ b/internal/common/helper.go @@ -11,7 +11,6 @@ import ( "path/filepath" "regexp" "strconv" - "sync" "metazone.cc/metalab/internal/model" @@ -19,81 +18,44 @@ import ( ) // assetHashes 静态资源文件哈希表(URL 路径 → 短哈希,文件不变哈希不变) -var ( - assetHashes map[string]string - assetOnce sync.Once -) +var assetHashes map[string]string -// ComputeAssetHashes 遍历 static 目录,计算每个文件的 CRC32作为版本号 +// ComputeAssetHashes 遍历 static 目录,计算每个文件的 CRC32 作为版本号 func ComputeAssetHashes(templateDir string) { assetHashes = make(map[string]string) - staticDir := filepath.Join(templateDir, "static") - filepath.WalkDir(staticDir, func(path string, d fs.DirEntry, err error) error { - if err != nil || d.IsDir() { - return nil - } - // 只处理 .js 和 .css - ext := filepath.Ext(path) - if ext != ".js" && ext != ".css" { - return nil - } - data, err := os.ReadFile(path) - if err != nil { - return nil - } - h := crc32.ChecksumIEEE(data) - shortHash := strconv.FormatUint(uint64(h), 16) - // 生成 URL 路径:/static/... - rel, _ := filepath.Rel(filepath.Dir(templateDir), path) - urlPath := "/" + filepath.ToSlash(rel) - assetHashes[urlPath] = shortHash - return nil - }) - // 也处理 shared/static 目录 - sharedDir := filepath.Join(filepath.Dir(templateDir), "shared", "static") - filepath.WalkDir(sharedDir, func(path string, d fs.DirEntry, err error) error { - if err != nil || d.IsDir() { - return nil - } - ext := filepath.Ext(path) - if ext != ".js" && ext != ".css" { - return nil - } - data, err := os.ReadFile(path) - if err != nil { - return nil - } - h := crc32.ChecksumIEEE(data) - shortHash := strconv.FormatUint(uint64(h), 16) - rel, _ := filepath.Rel(filepath.Dir(templateDir), path) - urlPath := "/" + filepath.ToSlash(rel) - assetHashes[urlPath] = shortHash - return nil - }) - // 也处理 admin/static 目录 - adminDir := filepath.Join(filepath.Dir(templateDir), "admin", "static") - filepath.WalkDir(adminDir, func(path string, d fs.DirEntry, err error) error { - if err != nil || d.IsDir() { - return nil - } - ext := filepath.Ext(path) - if ext != ".js" && ext != ".css" { - return nil - } - data, err := os.ReadFile(path) - if err != nil { - return nil - } - h := crc32.ChecksumIEEE(data) - shortHash := strconv.FormatUint(uint64(h), 16) - rel, _ := filepath.Rel(filepath.Dir(templateDir), path) - urlPath := "/" + filepath.ToSlash(rel) - assetHashes[urlPath] = shortHash - return nil - }) + // 前端主题:templates/MetaLab-2026/static → URL /static/ + walkStaticDir(filepath.Join(templateDir, "static"), "/static") + // 共享资源:templates/shared/static → URL /shared/static/ + walkStaticDir(filepath.Join(filepath.Dir(templateDir), "shared", "static"), "/shared/static") + // 管理后台:templates/admin/static → URL /admin/static/ + walkStaticDir(filepath.Join(filepath.Dir(templateDir), "admin", "static"), "/admin/static") log.Printf("[AssetHashes] computed %d file hashes", len(assetHashes)) } +// walkStaticDir 遍历目录,计算每个 .js/.css 的 CRC32,存入 assetHashes +func walkStaticDir(dir, urlPrefix string) { + filepath.WalkDir(dir, func(path string, d fs.DirEntry, err error) error { + if err != nil || d.IsDir() { + return nil + } + ext := filepath.Ext(path) + if ext != ".js" && ext != ".css" { + return nil + } + data, err := os.ReadFile(path) + if err != nil { + return nil + } + h := crc32.ChecksumIEEE(data) + shortHash := strconv.FormatUint(uint64(h), 16) + // 生成 URL 路径:urlPrefix + 相对于 dir 的子路径 + rel, _ := filepath.Rel(dir, path) + urlPath := urlPrefix + "/" + filepath.ToSlash(rel) + assetHashes[urlPath] = shortHash + return nil + }) +} + // AssetV 返回指定静态资源的哈希版本号(模板函数) func AssetV(path string) string { if h, ok := assetHashes[path]; ok {