蜘蛛抓取失败时,很多人第一反应是查源站:是不是服务挂了、是不是返回了 5xx。但在实际排查中,相当一部分抓取异常并不是源站的问题,而是请求还没到源站,就在 CDN、WAF 或者主机层面的防护规则里被拦下了。对于依赖 URL 被持续发现的站点来说,这类问题更隐蔽:源站日志干干净净,看起来像是“没被访问过”,其实请求早就被中间层挡回去了。
一、被中间层拦截时,日志会呈现什么样子
拦截不一定留下明显的错误,常见的表现有:
- 源站日志里完全看不到对应 URL 的请求,但页面在搜索结果里的缓存长期不更新。
- 访问日志大量出现 403、406、429,且 UA 与蜘蛛一致。
- 返回 200,但内容是一个校验页或跳转页,蜘蛛拿不到正文。
- 不同地区、不同 CDN 节点行为不一致:有的节点放行,有的节点拦截。
- 同一时间批量 URL 全挂,随后又自行恢复,像是触发了某种速率规则。
二、常见的误伤来源
1. CDN 的 Bot 管理与速率限制
不少 CDN 默认开启“已知机器人”识别,但规则库更新有滞后,或者把非主流蜘蛛一并归入可疑爬虫。另外,如果站点设置了单 IP 请求频率阈值,而蜘蛛在短时间内集中抓取,很容易被判定为攻击流量。
2. WAF 的规则集与自定义拦截
WAF 对 URL 中的特殊字符、参数与编码非常敏感。带大量查询参数的列表页、含中文或百分号编码的路径,偶尔会被规则误判。自定义拦截里如果写了过宽的关键词匹配,也会误伤正常页面地址。
3. 源站防火墙与自动封禁脚本
fail2ban 一类的工具会根据短时间内的高频请求自动封 IP。蜘蛛抓取本身就具备高频特征,如果阈值设置得过低,封禁几乎是必然的。
三、建议的排查顺序
- 从日志里挑一条抓取失败的 URL,记录完整时间点、UA 和返回码。
- 确认请求是否到达源站。用 curl 带上相同 UA,分别直连源站与走 CDN 域名测试。
- 对比两组响应:状态码、响应头、返回内容是否一致。
- 查看 CDN 与 WAF 的拦截日志,确认是否有匹配记录以及命中的规则编号。
- 检查主机防火墙与自动封禁列表,确认相关 IP 段是否在名单里。
- 定位到具体规则后做最小范围放行,而不是整段关闭防护。
四、放行时要注意的几点
- 不要只按 UA 放行。UA 可以随意伪造,仅凭 UA 放行等于给防护开了一个口子。
- 配合反向解析或公开 IP 段校验。先确认来源确实是蜘蛛,再决定放行规则。
- 优先放行必要路径。如果只是列表页被拦,就针对列表页的路径特征放行,而不是放开整站。
- 保留日志。放行之后仍要能追溯,方便下次出问题时快速定位。
五、放行之后还要观察什么
解除拦截不等于问题结束。接下来几天值得关注:源站日志里对应 URL 的请求量是否回升、返回码是否以 200 为主、抓取是否覆盖到更深层的页面,以及同一时段服务器负载的变化。如果请求量明显上升,要提前确认带宽和数据库连接数是否扛得住,避免刚放开拦截,又因为响应超时产生新的抓取失败。
提示:拦截规则与抓取策略都会随时间变化,今天合适的放行设置,过一段时间可能需要复核。把这类检查纳入固定的运维节奏,比临时救火更省事。