Skip to content

網頁抽取品質實測:Crawl4AI、Firecrawl、Jina Reader 與 Readability 差多少?

2026年8月22日 1 分鐘
TL;DR 抽取工具不能只比 HTTP 200;同一組 20 個 URL 要分別量正文、heading、table、code、link、metadata、雜訊、延遲與成本。本文先公開 corpus、adapter contract 與評分 gate,但因目前缺 Firecrawl credential 與四條同版本 raw run,尚不發佈勝負。
目錄
  1. 四條管線其實不是同一種東西
  2. 固定 20 個 URL,不用每次挑對自己有利的頁
  3. Adapter 只能回同一種 contract
  4. 評分先看必須保留什麼,再看輸出多漂亮
  5. 最容易做錯的四件事
    1. 把 fetch success 當 extraction success
    2. 四條管線用不同時間抓
    3. 只用字數判定完整
    4. 忘記抽取結果仍是不受信任輸入
  6. 目前能下的結論只有測試設計
  7. 參考資料

🌏 English version

已發布的實測規格。 本文已固定 20 個 URL、輸出 contract、評分 rubric 與失敗分類,但 2026-08-22 的環境沒有 FIRECRAWL_API_KEY,也尚未把四條 adapter 鎖在同一次 raw run。沒有 raw artifacts 就沒有排名;結果表要等同版本 raw run 完成後再補。

搜尋找到 URL 之後,下一步不是「把 HTML 丟給 LLM」而是先決定怎麼把正文抽出來。Crawl4AIFirecrawlJina ReaderMozilla Readability都能把網頁變成比較乾淨的內容,但它們處理 JS、正文判定、Markdown 結構、metadata 與成本的方式不同。

這篇不重做34 個爬蟲工具全景,也不拿官方 demo 頁互比。唯一問題是:給四條管線完全相同的 URL,誰保留了回答問題需要的內容,誰只是輸出看起來很乾淨的文字?

四條管線其實不是同一種東西

管線取得頁面主要輸出這次測試的設定
Crawl4AI本地 browser crawlerraw/fit Markdown、HTML、linkscleaned_html + default Markdown,不開 LLM filter
Firecrawl託管 scrape APIMarkdown、HTML、metadata/scrape,formats=markdown
Jina Reader託管 URL-to-text serviceLLM-friendly Markdown無 key Reader endpoint
Readability本地 DOM heuristicarticle HTML、text、title、bylinePlaywright 取 final DOM,再交給 Readability

Readability 本身不負責 browser fetch,也不把 HTML 轉成 Markdown。這次用同一個 Playwright fetcher 取得 final DOM,再用 Readability 判斷正文;否則比較到的是 HTTP client 差異,不是 extraction。Mozilla 文件也提醒,Readability 不負責 sanitize output,顯示抽取 HTML 前仍要經過 sanitizer。

Crawl4AI 官方把 raw_markdownfit_markdown 分開;fit 會經 content filter 移除區塊。為避免把 query-specific pruning 當成抽取能力,第一輪只比較預設 cleaned Markdown,第二輪才把 fit Markdown 當獨立 configuration。

固定 20 個 URL,不用每次挑對自己有利的頁

Corpus 以公開、可匿名讀取、能人工標示關鍵結構的頁面為主。每個 case 都要保存 retrieved_at、final URL、HTTP 狀態、content hash 與人工 ground-truth manifest。

ID類型URL必須保留的結構
docs-01API 文件https://playwright.dev/docs/authheadings、code、warning
docs-02Python 文件https://docs.python.org/3/library/pathlib.htmlAPI signatures、tables、code
docs-03Rust Bookhttps://doc.rust-lang.org/book/ch04-01-what-is-ownership.htmlprose、code、callouts
docs-04Crawl4AI docshttps://docs.crawl4ai.com/core/markdown-generation/nested headings、code、links
docs-05Firecrawl docshttps://docs.firecrawl.dev/features/scrapetabs、code、response fields
repo-01GitHub READMEhttps://github.com/mozilla/readabilitybadges、headings、code、links
repo-02GitHub READMEhttps://github.com/microsoft/playwright-mcpoption table、code、warnings
table-01HTML tablehttps://www.w3.org/TR/WCAG22/conformance tables、anchors
table-02Compatibility datahttps://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Set-Cookiesyntax、compatibility links
long-01Security guidehttps://cheatsheetseries.owasp.org/cheatsheets/Session_Management_Cheat_Sheet.htmllong hierarchy、code、lists
long-02Standards texthttps://www.rfc-editor.org/rfc/rfc9110.htmlnumbered sections、references
spa-01React docshttps://react.dev/learn/managing-stateclient-rendered navigation、code
spa-02Material docshttps://m3.material.io/styles/color/system/overviewrendered body、image captions
article-01Engineering bloghttps://blog.cloudflare.com/workers-ai/title、author/date、body、links
article-02Product bloghttps://www.mozilla.org/en-US/firefox/reader-view/body、images、CTA noise
zh-01台灣政府頁https://moda.gov.tw/繁中標題、導覽與正文分離
zh-02台灣法規頁https://law.moj.gov.tw/LawClass/LawAll.aspx?pcode=I0050021條文編號、段落、metadata
ja-01日本政府頁https://www.digital.go.jp/policies日文 headings、cards、links
pdf-01arXiv abstracthttps://arxiv.org/abs/2311.09735title、authors、abstract、DOI links
edge-01robots policyhttps://www.google.com/robots.txtplain text,不應被判定成空內容

這份清單不是永久不變。若頁面消失或大幅改版,manifest 要保留舊 hash 並新增 corpus version;不能默默換 URL 後把兩次分數接在一起。

Adapter 只能回同一種 contract

每個 adapter 的原始 response 完整保存,另外正規化成同一份 JSON:

{
  "case_id": "docs-01",
  "adapter": "crawl4ai-default",
  "adapter_version": "0.9.x",
  "requested_url": "https://playwright.dev/docs/auth",
  "final_url": "https://playwright.dev/docs/auth",
  "retrieved_at": "2026-08-22T00:00:00Z",
  "status": "success",
  "latency_ms": null,
  "cost_usd": null,
  "title": null,
  "author": null,
  "published_at": null,
  "markdown": null,
  "links": [],
  "raw_artifact": "raw/docs-01/crawl4ai-default.json",
  "error": null
}

null0 不可混用。沒有計費資料就是 null,不是零成本;沒有作者欄位也是 null,不是空字串。timeout、blocked、fetch error、parse empty、partial content 必須分開,否則 success rate 會把「抓到登入頁」算成成功。

評分先看必須保留什麼,再看輸出多漂亮

每個 case 的 ground truth 不保存整頁標準答案,而是保存 required_spansrequired_structuresknown_noise。人工審查者不知道輸出來自哪個 adapter,再分別打:

  1. 正文完整度:required spans 找回多少。
  2. 雜訊比例:navigation、cookie banner、推薦卡、footer 等 known noise 佔多少。
  3. 結構保存:heading 層級、table、code block、list、link 是否還能辨識。
  4. Metadata:title、author、published time、canonical URL 是否正確。
  5. 可追溯性:輸出 link 能否回到原始 href,內容是否保留足以定位的 section。
  6. 效率:p50/p95 latency、request 數、付費金額與 output bytes。

不要壓成單一總分。正文少一半但 latency 很低,不該和內容完整但稍慢互相抵銷。Regression gate 應分開設定,例如:required span recall 不得下降、code block 保存率不得下降、p95 latency 不得惡化超過事先接受的幅度。

最容易做錯的四件事

把 fetch success 當 extraction success

HTTP 200 可能是 consent page、登入頁、bot challenge 或只有 app shell。必須先驗證 title、required span 與最小正文長度,再標 success。

四條管線用不同時間抓

新聞首頁、文件與 SPA 會更新。每個 case 的四個 adapter 應在同一個短 window 內跑完,並保存 source snapshot;否則差異可能來自頁面變了。

只用字數判定完整

字多可能只是導覽與 footer。字少也可能是精準抽取。完整度應對 required spans,雜訊另算。

忘記抽取結果仍是不受信任輸入

HTML、Markdown 與 metadata 都可能含提示注入或惡意 markup。Mozilla 明確說 Readability 不做 sanitization;其他服務輸出 Markdown 也不代表內容安全。抽取後仍要 sanitize、保留 provenance,並和 tool instruction 分離。

目前能下的結論只有測試設計

四個工具的官方能力可以描述,勝負還不能。Crawl4AI 提供本地 browser 與可調 Markdown/filter pipeline;Firecrawl 提供託管 scrape 與多種 formats;Jina Reader 用 URL prefix 快速取得 LLM-friendly text;Readability 是最輕的本地 article heuristic,但 fetch、render、Markdown conversion 與 sanitization 都要自己補。

等四條 adapter 在同一個 corpus version 跑完、raw artifacts 入庫、人工標註完成,本文再加入結果表與逐類失敗案例。少任何一項,都只是在比較產品說明,不是實測。

參考資料