Nginx 通过 if + $http_user_agent 实现轻量级 UA 灰度安全策略,支持拦截恶意爬虫、按 UA 启用增强安全头、路由至不同后端,但 UA 可伪造,仅作辅助策略。

直接用 Nginx 的 if 指令配合 $http_user_agent 变量做判断,是最轻量、最可控的 User-Agent 灰度安全策略下发方式。它不依赖外部组件, reload 即生效,适合快速拦截恶意爬虫、放行内部工具或定向推送新安全头。
识别并拦截高风险 User-Agent
很多扫描器、暴力破解工具、已知漏洞利用脚本会使用固定或特征明显的 User-Agent 字符串。你可以直接在 location 块中拦截并返回 403:
- 用正则匹配常见恶意标识,比如
"sqlmap|nmap|nikto|wget.*-r|curl.*-I" - 注意写法要加引号和
~*(忽略大小写),避免误伤正常请求 - 示例配置:
location / { if ($http_user_agent ~* "(sqlmap|nmap|nikto|wget.*-r|curl.*-I)") { return 403; } # 后续 proxy_pass 或静态服务 }
对特定 UA 强制启用增强安全头
不是所有客户端都支持最新安全机制。你可以只对现代浏览器(如 Chrome、Firefox 最新版)下发严格 CSP 或 HSTS,而对老旧 UA 保持兼容性头:
- 用
map指令预定义变量,比反复 if 更高效 - 例如:
map $http_user_agent $csp_policy { default "default-src 'self'"; ~* "Chrome/[9-99]" "default-src 'self'; script-src 'self' 'unsafe-inline'"; } - 再在 server 或 location 中:
add_header Content-Security-Policy $csp_policy;
按 UA 类型路由到不同后端(灰度+安全双控)
把灰度发布和安全策略结合:让测试工具、内部爬虫走带 WAF 规则的新版后端,普通用户走稳定版;或让移动端 UA 强制走 HTTPS+HSTS,PC 端保留 HTTP 兼容入口:
- 先定义 upstream 分组:
upstream stable_backend { server 10.0.1.10:8080; }和upstream secure_canary { server 10.0.1.20:8081; } - 用 map 匹配 UA 类别:
map $http_user_agent $backend_group { default stable_backend; ~* "Postman|curl|internal-scan" secure_canary; } - 在 location 中:
proxy_pass http://$backend_group;
注意事项与避坑点
User-Agent 极易伪造,所以它不能作为唯一认证依据,仅适用于“策略分级”或“辅助识别”。关键安全控制(如权限校验、敏感操作)必须由后端完成。
- 避免在 if 中嵌套 proxy_pass,Nginx 官方明确不推荐
- 正则尽量用
~*而非~,防止大小写漏判 - 若需复杂逻辑(如 UA + Cookie + IP 组合判断),建议改用 nginx-lua 模块,而非硬塞 if 块
- 上线前务必用
nginx -t校验语法,避免 reload 失败导致服务中断











