蜘蛛沿站内連結前進,路径一旦打结,就會出現反复抓同一個地址、URL 越爬越長、抓取量上去了但有效頁面没增加的情况。這類問题不會报错,只有翻訪問日誌、自己用爬虫走一遍,才會看到痕迹。下面按识別、拆解、预防三步来说。
路径打结的常见形態
- 參數循环:篩選、排序、會话标识、跟踪參數自由组合,生成一批只有參數不同的地址,頁面之間又互相带連結,蜘蛛可以一直往深處走。
- 分頁與篩選互相指向:篩選结果頁里放分頁連結,分頁頁里又放篩選連結,两個维度相乘,路径數量成倍增長。
- 标簽、归档、日歷连环:标簽頁指向文章,文章底部又指向全部标簽;日期归档頁互相指向前後月份,越往前内容越少。
- 列表與詳情互相回流:詳情頁的“相關推荐”“返回列表”指回聚合頁,聚合頁再指向詳情,形成閉合回路。
怎么判断是循环,而不是正常抓取
正常抓取也會重复訪問同一個頁面,区別在于路径是否收敛。循环的特征是:同一批内容被不同的地址反复覆盖,抓取次數增加,獨立 URL 數量却增長缓慢。
訪問日誌里的信号
- 同一路径前缀下出現大量參數组合,URL 越来越長。
- 蜘蛛在某一目錄下停留時間很長,但抓到的有效 URL 很少。
- 抓取時間集中在少數几個模板頁,詳情頁反而很少被碰。
- 响應時間随着抓取量上升逐渐變慢,說明循环也在消耗服務器。
自己爬一遍
用爬虫工具從首頁出發,設定深度上限(比如 5 层)和每层 URL 上限,看抓取结果的深度分布。如果深层出現大量參數相同、内容相似的地址,基本可以确定路径没收敛。也可以只抓取某個目錄,观察它是否會绕回自己。
拆解思路:给每條路径留一個出口
- 參數收敛:能合並的參數合並,能去掉的跟踪參數去掉;确實要保留的篩選组合,用 canonical 指向主版本,並且不要在頁面里生成可被跟進的連結。
- 把分頁和篩選分開:分頁只沿一個维度推進,篩選结果頁不輸出分頁連結,需要浏览更多时用“加载更多”由前端處理,不生成新地址。
- 限制标簽與归档:只保留有内容、有检索價值的标簽;归档頁合並到少數几個入口,不要做成年月日互相連結的網。
- 控制相關推荐:詳情頁底部的推荐可以指向同類内容,但不要把所有模块都连回列表頁;列表頁與詳情頁之間保留一條清晰的上下級關系即可。
- 给無限内容设邊界:日歷、论坛分頁、搜尋结果這類會無限延伸的頁面,明确一個停止点,或者用 robots.txt 屏蔽無價值的深层參數路径。
循环與服務器负载是连在一起的
循环抓取會放大請求量,占用带宽和資料库查询。發現抓取速率異常上升时,可以先看日誌里的响應時間和狀態碼分布,再决定是否用 429 配合 Retry-After 给蜘蛛限速。限速是缓解手段,真正要處理的還是路径本身:路径不收口,限速只是让循环走得慢一点。
上线後的检查清單
- 從首頁出發模拟抓取,設定深度上限,检查是否有目錄在自我循环。
- 抽查篩選、排序、分頁组合,確認不會生成新的可抓連結。
- 检查标簽頁、归档頁之間的互鏈,避免形成閉环。
- 观察日誌中同一模板頁的抓取占比,超過预期就回头查内鏈。
- 服務器變慢时先確認是不是循环带来的額外压力,再調整抓取节奏。
路径循环的代價不是流量,而是抓取時間被稀释:蜘蛛把有限的時間花在了重复的地址上,真正需要更新的頁面就排到了後面。