如何利用proxy_cache_key变量实现按业务维度细分的高效缓存隔离策略?
- 内容介绍
- 文章标签
- 相关推荐
本文共计746个文字,预计阅读时间需要3分钟。
为了让+Nginx+的配置更高效,以下是一个简化的配置开头内容:
按域名隔离:避免多站点缓存互相污染
多个域名共用一个缓存区时,/about 在 example.com 和 test.com 下本应是两份内容。只靠 proxy_cache_path 分开还不够,必须在 key 里显式带上 $host:
- 在
http块中定义独立缓存区:proxy_cache_path /var/cache/nginx/site_a ... keys_zone=site_a:10m;proxy_cache_path /var/cache/nginx/site_b ... keys_zone=site_b:10m; - 在对应
server块中绑定并构造 key:proxy_cache site_a;proxy_cache_key "$host$request_uri$is_args$args";
这样 example.com/about 和 test.com/about 的哈希值完全不同,物理上也写入不同目录,彻底断开干扰。
按终端类型区分:PC 与移动端不共用缓存
Next.js 或 SSR 应用常根据 User-Agent 返回不同 HTML。若缓存 key 不含终端标识,手机用户可能拿到 PC 版页面。
- 用
map提前提取设备类型(避免 key 中写复杂正则):map $http_user_agent $mobile_flag {<br> ~*"(iPhone|Android|Mobile)" "mobile";<br> default "desktop";<br>}
- 将
$mobile_flag加入 key:proxy_cache_key "$host$request_uri|$mobile_flag";
注意控制变量长度,$mobile_flag 比完整 $http_user_agent 更安全,也利于命中率。
按关键业务参数过滤:保留有用、剔除干扰
Next.js 的 ?lang=zh 或 ?region=jp 影响服务端渲染结果,必须进 key;而 utm_source=weibo 或 _ga=GA1.2.xxxx 纯属分析用途,必须排除。
- 用
map提取有效参数:map $args $cache_lang {<br> ~(lang=)([^&]+) $2;<br> default "";<br>}
- 同样处理 cookie 中的关键字段(如主题、登录态):
map $http_cookie $cache_theme {<br> ~theme=(dark|light) $1;<br> default "";<br>}
- 组合最终 key:
proxy_cache_key "$host$request_uri|$cache_lang|$cache_theme";
不拼全 $args,也不无差别包含所有 cookie,既保精准,又防 key 膨胀导致缓存失效。
按请求方法或认证上下文隔离:防止越权与误覆盖
GET 和 HEAD 请求语义不同;带 Authorization 的接口属于私有资源,绝不能和匿名请求共享缓存。
- 基础增强写法:
proxy_cache_key "$request_method|$host$request_uri"; - 涉及登录态的 API 缓存:
proxy_cache_key "$request_method|$host$request_uri|$http_authorization|$cookie_session_id";
这里 $http_authorization 是 Header 值,$cookie_session_id 是 Cookie 字段,两者任一变化都会生成新 key,保障权限边界清晰。
本文共计746个文字,预计阅读时间需要3分钟。
为了让+Nginx+的配置更高效,以下是一个简化的配置开头内容:
按域名隔离:避免多站点缓存互相污染
多个域名共用一个缓存区时,/about 在 example.com 和 test.com 下本应是两份内容。只靠 proxy_cache_path 分开还不够,必须在 key 里显式带上 $host:
- 在
http块中定义独立缓存区:proxy_cache_path /var/cache/nginx/site_a ... keys_zone=site_a:10m;proxy_cache_path /var/cache/nginx/site_b ... keys_zone=site_b:10m; - 在对应
server块中绑定并构造 key:proxy_cache site_a;proxy_cache_key "$host$request_uri$is_args$args";
这样 example.com/about 和 test.com/about 的哈希值完全不同,物理上也写入不同目录,彻底断开干扰。
按终端类型区分:PC 与移动端不共用缓存
Next.js 或 SSR 应用常根据 User-Agent 返回不同 HTML。若缓存 key 不含终端标识,手机用户可能拿到 PC 版页面。
- 用
map提前提取设备类型(避免 key 中写复杂正则):map $http_user_agent $mobile_flag {<br> ~*"(iPhone|Android|Mobile)" "mobile";<br> default "desktop";<br>}
- 将
$mobile_flag加入 key:proxy_cache_key "$host$request_uri|$mobile_flag";
注意控制变量长度,$mobile_flag 比完整 $http_user_agent 更安全,也利于命中率。
按关键业务参数过滤:保留有用、剔除干扰
Next.js 的 ?lang=zh 或 ?region=jp 影响服务端渲染结果,必须进 key;而 utm_source=weibo 或 _ga=GA1.2.xxxx 纯属分析用途,必须排除。
- 用
map提取有效参数:map $args $cache_lang {<br> ~(lang=)([^&]+) $2;<br> default "";<br>}
- 同样处理 cookie 中的关键字段(如主题、登录态):
map $http_cookie $cache_theme {<br> ~theme=(dark|light) $1;<br> default "";<br>}
- 组合最终 key:
proxy_cache_key "$host$request_uri|$cache_lang|$cache_theme";
不拼全 $args,也不无差别包含所有 cookie,既保精准,又防 key 膨胀导致缓存失效。
按请求方法或认证上下文隔离:防止越权与误覆盖
GET 和 HEAD 请求语义不同;带 Authorization 的接口属于私有资源,绝不能和匿名请求共享缓存。
- 基础增强写法:
proxy_cache_key "$request_method|$host$request_uri"; - 涉及登录态的 API 缓存:
proxy_cache_key "$request_method|$host$request_uri|$http_authorization|$cookie_session_id";
这里 $http_authorization 是 Header 值,$cookie_session_id 是 Cookie 字段,两者任一变化都会生成新 key,保障权限边界清晰。

