nginx缓存是抵御恶意爬虫和ddos的核心“流量减压阀”,通过缓存静态与高命中率动态内容、差异化缓存键、缓存+限流联动及健康监控,实现后端保护。

利用 Nginx 缓存机制抵御恶意爬虫和 DDoS 攻击,核心不是“完全挡住”,而是让后端不被压垮——把可缓存的请求在 Nginx 层直接响应,不发往后端;对不可缓存但高频的恶意行为,则配合限流与连接控制快速拦截。缓存本身不防攻击,但它是最有效的“流量减压阀”。
优先缓存静态资源与高命中率动态内容
大量爬虫和低质量 DDoS 请求集中在首页、列表页、API 文档等公开路径。只要这些内容更新不频繁,就应强制缓存:
- 用 proxy_cache_valid 对常见状态码设置不同缓存时间:例如
proxy_cache_valid 200 301 302 10m;(成功响应缓存 10 分钟),proxy_cache_valid 404 1m;(错误页也缓存 1 分钟,防反复扫不存在路径) - 对明确无用户态差异的接口(如 /status、/health、公共配置 API),加 proxy_cache_bypass 和 proxy_no_cache 配合,确保即使带参数或 Cookie 也走缓存
- 避免缓存带 Set-Cookie 或 Vary: Cookie 的响应——否则缓存失效快、命中率低,还可能污染共享缓存
用缓存+键值分离应对“伪合法”爬虫
真实浏览器访问常带 User-Agent、Referer、Accept-Encoding,而多数爬虫缺失或固定。Nginx 可据此生成差异化缓存键:
- 定义缓存键时排除干扰字段:
proxy_cache_key "$scheme$request_method$host$uri$is_args$args";(不包含 $http_user_agent) - 若需区分移动端/PC,可加入
$http_ua_platform等自定义变量,但避免用全量 $http_user_agent——防缓存碎片化 - 对已知爬虫 UA(如 python-requests、curl、masscan),用 map 指令将其统一映射为一个缓存键前缀,让所有爬虫共用一份缓存,大幅降低后端压力
缓存层叠加主动防御策略
单靠缓存无法处理高频刷新、参数遍历类攻击。必须与限流、连接控制联动:
- 对未命中缓存的请求(
$upstream_cache_status = MISS或MISS),在 location 中启用更严格的 limit_req:例如limit_req zone=miss_limit burst=3 nodelay;,防止爬虫反复穿透缓存打后端 - 将缓存过期时间(
proxy_cache_valid)与 proxy_cache_lock 结合:开启 lock 后,首个未命中请求去后端取数据,其余同 key 请求等待该响应并写入缓存,避免“缓存雪崩式并发回源” - 对 /api/ 等关键路径,即使内容不可缓存,也启用 proxy_buffering off + proxy_cache_min_uses 3:同一 URL 被访问 3 次后再缓存,兼顾冷启动与热点识别
监控缓存健康度,及时发现绕过行为
缓存是否真正起效,不能只看配置是否生效,要看实际命中率与异常模式:
- 在日志中记录 $upstream_cache_status 字段,统计 HIT / MISS / EXPIRED / BYPASS 比例;持续低于 70% 的 HIT 率需检查缓存键设计或后端响应头(如 Cache-Control: no-store)
- 对高频 MISS 的 IP 段,结合 $request_time 和 $upstream_response_time 判断是否为慢速爬虫——若 request_time 远大于 upstream_response_time,大概率是低速连接攻击,应配合 client_header_timeout 和 reset_timedout_connection on 快速切断
- 定期用
curl -I检查关键路径响应头,确认是否返回X-Cache: HIT或Age头,验证缓存链路完整











