很多站点在服务器监控上看到的平均响应时间很漂亮,两三百毫秒,但抓取日志里的抓取量就是上不去,或者一批页面反复抓取失败。问题往往不在平均值,而在长尾:少数请求慢到几十秒,恰好被蜘蛛碰上。
平均值藏起来的那部分请求
平均响应时间是把所有请求加总再除以数量。一个 30 秒的请求混在 99 个 200 毫秒的请求里,平均值只被拉高一点点,监控面板上看不出异常。但蜘蛛是按请求逐个走的,碰上那一个慢请求,它这一轮就可能超时断开,并把这次经历记到这个地址上。
更实际的做法是看分位数。P95、P99 表示最慢的 5%、1% 请求需要多久,这个数值才更接近蜘蛛偶尔会遇到的真实情况。
从抓取日志里能看出什么
- 响应时间分布:别只看平均值,按小时统计慢请求占比,看它是否集中在某些时段。
- 超时与连接中断的数量:蜘蛛主动断开,通常意味着它已经等不及了。
- 状态码构成:5xx、超时、连接重置混在一起,指向服务器侧,而不是页面内容问题。
- 抓取间隔变化:同一批 URL 的抓取间隔突然拉长,往往对应这段时间响应变慢。
拖慢响应的常见环节
- 缓存未命中回源。蜘蛛走的路径和真实用户不一定相同,命中的缓存层也可能不一样,回源一多就慢。
- 数据库慢查询。列表页、聚合页在数据量涨上来之后最容易暴露,页面越大越明显。
- 第三方接口。页面输出依赖外部接口,接口一慢整页都跟着慢,而这部分耗时常常不在自己的监控里。
- 大文件与附件。图片、PDF 直出、没有走 CDN 的文件请求,会占住连接和带宽。
- 并发限流。蜘蛛并发稍高就触发全站保护,正常请求也被一起拖住。
抓取变慢和抓取失败是两件事
页面响应从 300 毫秒变成 3 秒,蜘蛛不会立刻放弃,但它会减少对这个目录的抓取频次,把预算挪到别处。这个过程是渐进的,等到抓取量明显下滑时,通常已经持续了一段时间。所以对慢的容忍度要比对错的容忍度更低,慢是失败的先行指标。
反过来,偶尔一次失败并不致命。蜘蛛对单个 URL 的失败有重试机制,怕的是同一批 URL 反复失败,让它对整个目录降低信任。
对蜘蛛和用户要分开看
不必专门给蜘蛛开一条通道,但限速策略应该认得它。触发保护时,与其让连接挂着不响应、读一半直接断掉,不如明确返回 503 并带上 Retry-After,让蜘蛛知道什么时候再来。连接长时间挂起,对蜘蛛来说是最难处理的一种状态,它既拿不到内容,也拿不到明确的信号。
如果某个页型确实重、算得慢,可以考虑对蜘蛛返回一个内容等价但更轻的版本,或者把它拆成多个更小的页面,而不是让它每次都走完整条重链路。
排查顺序
先从抓取日志里挑出响应最慢的一批 URL,按目录归类,看它们是不是集中在同一类模板;再去服务器侧对照那段时间的慢查询、缓存命中率和外部接口耗时。多数情况下问题会落到某一两个页型上,而不是全站均匀变慢。找到页型之后,处理方式通常是缓存、异步化或者拆分,而不是整体加机器。
蜘蛛感受到的站点速度,是它自己那批请求的分布,不是监控面板上那条平均线。
在监控里加一条 P95 或 P99 的曲线,成本不高,却能在慢请求还没变成抓取失败之前提前发现问题。