Nuxt 3中如何为静态文件添加缓存策略?现有方案失效求助
解决Nuxt 3中静态资源缓存头不生效问题
问题分析
你遇到的核心问题有两个:一是自定义Server Middleware仅匹配图片资源,未覆盖CSS/JS等文件;二是routeRules配置未生效。本质原因包括正则匹配缺陷、Middleware执行顺序问题,以及Nuxt静态资源处理的优先级逻辑。
解决方案一:修正Server Middleware并调整执行顺序
1. 修复正则匹配逻辑
原正则的(.+)会导致部分路径匹配失败,且未处理带查询参数的URL。修改后代码如下:
export default defineEventHandler(async (event) => { // 移除URL中的查询参数,避免干扰后缀匹配 const cleanUrl = event.node.req.url.split('?')[0]; let maxage; if (process.env.NODE_ENV === "production") { // 不区分大小写匹配目标资源后缀,结尾锚定确保完整匹配 const isStaticAsset = /\.(jpg|jpeg|gif|png|ico|svg|css|js|mjs|woff)$/i.test(cleanUrl); maxage = isStaticAsset ? 60 * 60 * 24 * 30 : 60 * 60; appendHeader(event, "Cache-Control", `public, max-age=${maxage}, s-maxage=${maxage}`); } else { maxage = 120; appendHeader(event, "Cache-Control", `public, max-age=${maxage}, s-maxage=${maxage}`); } })
2. 调整Middleware执行顺序
Nuxt按文件名顺序执行Server Middleware,将你的middleware文件命名为01-cache-header.ts(前缀数字确保优先级高于默认静态资源处理),放在server/middleware目录下。
解决方案二:正确配置Route Rules
1. 规范配置格式与变量定义
确保缓存头格式符合HTTP标准,且变量正确定义:
const monthCache = 60 * 60 * 24 * 30; const yearCache = 60 * 60 * 24 * 365; export default defineNuxtConfig({ routeRules: { // 匹配/img目录下所有资源 "/img/**": { headers: { 'cache-control': `public, max-age=${monthCache}, s-maxage=${monthCache}` } }, // 匹配Nuxt打包后的静态资源目录 "/_nuxt/**": { headers: { 'cache-control': `public, max-age=${yearCache}, s-maxage=${yearCache}` } }, // 可选:匹配根目录下的零散静态资源 "/*.{jpg,jpeg,gif,png,ico,svg,css,js,mjs,woff}": { headers: { 'cache-control': `public, max-age=${monthCache}, s-maxage=${monthCache}` } } } })
2. 验证生产环境有效性
routeRules部分配置仅在生产构建后生效,运行npm run build && npm run preview测试,不要在开发环境npm run dev中验证。
解决方案三:使用Nitro全局钩子(最高优先级)
如果前两种方法仍不生效,直接通过Nitro钩子全局控制响应头,优先级最高:
export default defineNuxtConfig({ nitro: { hooks: { 'render:response'(response, { event }) { const cleanUrl = event.node.req.url.split('?')[0]; let maxage = 60 * 60; // 默认1小时缓存 if (process.env.NODE_ENV === "production") { if (/\.(jpg|jpeg|gif|png|ico|svg|css|js|mjs|woff)$/i.test(cleanUrl)) { maxage = 60 * 60 * 24 * 30; // 静态资源30天缓存 } } else { maxage = 120; // 开发环境2分钟缓存 } response.headers['cache-control'] = `public, max-age=${maxage}, s-maxage=${maxage}`; } } } })
内容的提问来源于stack exchange,提问作者Davod naroea
相关产品推荐
相关产品推荐

