map指令通过匹配$sent_http_content_type动态设置expires,解耦缓存时长与资源类型,比基于路径的location更准确健壮;需定义在http块,正则前加~*不区分大小写,default"epoch"兜底。

用 map 指令动态设置 expires,核心是把缓存时长和资源类型解耦,避免一堆重复的 location 块。它不依赖文件路径或扩展名,而是基于响应头中的 Content-Type 做判断,更贴近真实返回内容,也更健壮。
map 必须定义在 http 块中,且匹配 $sent_http_content_type
这个变量代表 Nginx 实际发给浏览器的 Content-Type 值(注意不是请求头)。所以后端必须正确设置该头,否则匹配会失效。正则前加 ~* 表示不区分大小写,能覆盖 Image/PNG、TEXT/CSS 这类非标准写法。
-
default "epoch"是安全兜底:等效于Expires: Thu, 01 Jan 1970...,强制不缓存 - 匹配
~*^text/可同时覆盖text/html、text/css、text/javascript - 字体类型建议统一用
~*^font/和~*^application/font-两条,覆盖 woff2/ttf/woff/eot 等主流格式
常见类型推荐缓存时长与写法
不同资源更新频率差异大,缓存时间要合理分级:
-
HTML / 动态文本:
~*^text/html "-1"或"epoch",禁用缓存 -
CSS / JS:
~*^text/css "1M"、~*^application/javascript "1M",设 1 个月较稳妥;若配合哈希命名(如app.a1b2c3.js),可升到"1y"并加immutable -
图片 / 音视频:
~*^image/ "1w"、~*^video/ "1w",普通站点设 1 周足够;CDN 场景可延长至"1y" -
字体 / PDF / 字体相关:
~*^font/ "1y"、~*^application/pdf "1y",这类资源极少变动,适合长期缓存
server 或 location 中直接引用变量
定义好 map 后,在需要控制缓存的位置直接写 expires $expires_time; 即可。它会自动根据本次响应的 Content-Type 查表取值。
- 放在
server块里,对整个站点生效 - 放在某个
location里,只影响该路径下的响应(比如只对/static/下资源启用) - 注意:如果同一 location 内同时存在
expires指令和add_header Cache-Control,两者要语义一致,避免冲突
对比按后缀匹配的 location 方式
用 location ~* \.js$ 看的是请求路径,而 map 看的是真实响应类型。这意味着:
- 后端可能把 JS 返回为
text/plain,此时location匹配不到,但map仍可按实际类型处理 - 某些接口返回 JSON,但路径含
.html,location会误判,map更准确 -
map规则集中维护,新增类型只需改一处;location易分散、难统一

















