站点运营

站点运营:前端渲染與正文可见性自查,別让蜘蛛只拿到一個空壳頁面

不少站点把正文交给前端脚本渲染,抓取工具請求到的 HTML 里只有一個空的挂载节点和几行脚本,内容自然無從發現。這篇文章從自查方法讲起,說明如何用禁用 JS 的浏览器和直接請求源碼核對正文可见性,並给出服務端渲染、预渲染、静態生成等几種落地方式,以及改完之後如何驗證内容一致性。

站点运营

站点运营:前端渲染與正文可见性自查,別让蜘蛛只拿到一個空壳頁面

為什么蜘蛛看到的和你看到的不一样

在浏览器里打開頁面,内容齐全、排版正常,于是很多人預設抓取工具看到的也是同一份東西。實际情况是,你看到的是浏览器执行完 JavaScript 之後的頁面,而抓取工具第一眼拿到的往往是服務器返回的原始 HTML。如果正文、列表、連結都是脚本执行後才插入的,那么初始 HTML 里可能只有一個空的挂载节点和几行脚本引用。内容不是不存在,只是出現得太晚,甚至根本不出現。

這不是某個框架的错,而是渲染方式的選擇問题。問题在于,很多站点是在上线之後才發現這件事,此时頁面已经被抓過一轮,索引里的狀態和實际内容對不上。

三步自查:確認正文到底在不在初始 HTML 里

第一步:直接請求源碼

用命令行工具带上常见抓取工具的 User-Agent 請求目标頁,把返回的 HTML 儲存下来,然後在文本里搜尋正文中的一句话。搜不到,說明正文不在初始响應里。這一步比看浏览器「查看源代碼」更可靠,因為有些浏览器的源碼视图會顯示执行後的 DOM。

第二步:關掉 JavaScript 再看一遍

在浏览器設定里禁用 JavaScript 後重新打開頁面。如果頁面只剩導航骨架、加载動画或一片空白,而正文完全没有出現,那基本可以確認内容依赖脚本渲染。這個方法简單,适合批量抽查栏目頁、詳情頁、列表頁。

第三步:核對連結是否是真實連結

列表頁和分頁導航尤其要注意。如果翻頁、進入詳情都靠点击事件跳轉,HTML 里没有带 href 的 a 标簽,那么爬虫在列表頁就找不到下一层的入口。把鼠标悬停在連結上,看狀態栏是否顯示地址,是一個快速的判断方式。

常见的几種「藏内容」寫法

  • 正文通過接口异步获取,首屏只有一個骨架屏;
  • 列表使用無限滚動,没有對應的分頁地址;
  • 标簽頁、折叠面板里的内容只在点击後才請求;
  • 图片和文字都用懒加载,滚動到可视区域才插入 DOM;
  • 整站是單頁應用,路由變化不改變服務器返回的 HTML。

這些寫法對用戶体驗未必是坏事,但對抓取来说,入口和内容都變得不确定。尤其当站点内容量大、更新频繁时,抓取到的空頁面會占用訪問額度,却没有带来任何有效發現。

處理思路:從轻到重

不必一上来就重寫整個前端,可以按成本從低到高選擇。

  1. 關键内容服務端輸出。把标题、正文首段、主要導航和列表連結改為服務端渲染,交互部分仍交给前端。改動范围小,收益直接。
  2. 静態生成。内容更新频率不高的站点,可以在构建时生成 HTML,部署後直接返回完整頁面,抓取和訪問速度都好。
  3. 预渲染。對少量重点頁面在构建或請求时生成静態快照,适合内容不依赖登入態的展示型頁面。
  4. 服務端渲染。内容型站点、需要實时資料的頁面可以考虑,但要做好缓存,否則會明顯增加服務器压力。
  5. 分頁連結改為真實地址。無限滚動保留给用戶,同时提供可訪問的分頁 URL,两者並存。
需要强調的是,渲染方案不是用来對付抓取的工具。如果给抓取工具返回一份内容,给用戶返回另一份内容,或者把正文藏在用戶看不到的位置,性质就變了。做法上應当保持两版内容一致,只是让内容更早出現。

改完之後怎么驗證

改動上线後,別只看首頁。挑几個不同類型的頁面:栏目首頁、带分頁的列表頁、内容詳情頁、标簽聚合頁。逐個請求源碼,確認标题、正文、主要連結都在初始 HTML 中。同时對照訪問日誌,看抓取工具請求這些地址时的响應狀態和返回体积是否正常,体积突然變小通常意味着内容又回到了脚本里。

另外记得检查渲染版本的样式和交互有没有因為改動而错位,尤其是服務端輸出與前端接管之間的衔接部分。内容可见性和頁面体驗不是二選一,两個都要稳住。

把它纳入日常巡检

模板改動、前端框架升級、接口结构調整,都可能無意中让正文重新回到脚本里。可以在每次上线後固定抽查一两個頁面,或者把「源碼中是否包含正文關鍵詞」做成简單的自動检查。這類問题發現得越早,處理成本越低。