F2T相談する
データ分析・基盤

Firecrawlとは。料金と使い方、競合サイトを丸ごとデータ化する方法

13分で読めます
Firecrawlとは。料金と使い方、競合サイトを丸ごとデータ化する方法

競合30社のサービスページを全部集めてくれ、と頼まれたことがある。手作業なら、1社ずつ開いてコピーして、表に貼って、を数日かけて繰り返す仕事だ。Firecrawlを使ったら、その日の午後には終わっていた。

Webサイトのデータをまとめて欲しくなる場面は、経営の現場に意外と多い。競合の価格やサービス内容の一覧化。旧サイトから新サイトへの記事移行。自社の問い合わせ対応をAIに任せるための、社内マニュアルのデータ化。どれも「人間が1ページずつ開いてコピーする」とキリがない。Firecrawlは、この「1ページずつ」を丸ごと肩代わりするツールだ。

私はAIエージェント組織を自分の業務で毎日動かしている。その中でWebからデータを集める作業は日常的に発生する。この記事は、実際にFirecrawlを触った記録をもとに、何ができて、いくらかかって、自社に入れる価値があるかを判断できるところまで書く。コードも載せるので、手を動かす人はそのまま試せる。

Firecrawlとは。Webサイトを丸ごとデータ化するツール

一言でいうと、任意のWebサイトを開いて、中身をAIが読みやすい形(Markdown)に整えて返してくれるツールだ。OSSとして公開されていて、自前サーバーで無料運用もできるし、登録するだけで使えるSaaS版もある(Firecrawl公式)。

技術的なポイントは、JavaScriptで描画される最近のサイトにも対応していること。昔ながらのデータ収集ツールは、ブラウザで見たときの画面と、プログラムが取得する中身が食い違うサイトでよく壊れた。Firecrawlはブラウザで実際に描画した後の状態を取りに行くので、人間が見ている画面とほぼ同じ情報が取れる。

できることを整理すると、こうなる。

  • URLのリストや sitemap.xml から、サイトの全ページを一括取得
  • ページの中の必要な部分だけを抜き出す
  • ログインや動的な読み込みが必要なページも、描画後の中身を取得
  • 取得結果を、そのままAI(LLM)に渡せる形で出力

最後の「そのままAIに渡せる形」が、他のツールとの一番の違いになる。従来はデータを取った後に、AIが読める形へ整える前処理がひと仕事だった。そこがほぼ要らなくなる。

Firecrawlの料金。無料枠500ページから

先に料金の全体像を出す。以下は2026年3月時点の公式プランだ。

プラン

月額

クレジット/月

レート制限

Free

$0

500

10リクエスト/分

Hobby

$16

3,000

20リクエスト/分

Standard

$83

100,000

100リクエスト/分

Growth

要問合せ

カスタム

カスタム

課金の単位は「クレジット」で、1ページ取得するごとに1クレジット消費する。無料プランの500クレジットは、500ページ分だ。

まず試すだけなら無料枠で十分足りる。1ページの取得結果を見れば、自社の用途に合うかどうかはすぐ判断がつく。個人プロジェクトや小規模な業務ならHobby($16)で足りることが多い。月3,000ページあれば、中規模のサイトを数回まるごとクロールできる。継続的に大量のページを集める運用に育ったら、Standard以上を検討する流れになる。

料金を気にせず、データを外に出したくない事情がある場合は、OSS版を自前サーバーで動かす選択肢もある。この場合クレジットの概念もレート制限もない。ただし動かすにはブラウザ描画用の環境(Chromium)が必要で、メモリは最低4GBほど見ておく。運用の手間とサーバー代を、SaaSの月額と天秤にかける判断になる。

実際に使ってみる。5分で動く

ここからは手を動かす人向け。経営判断だけ知りたい方は「自社でやるか、外部に頼むか」まで飛ばして構わない。

Python SDKを入れて、APIキーを渡すだけで始まる。

pip install firecrawl-py

APIキーはFirecrawlのダッシュボードで取得する。

from firecrawl import FirecrawlApp

app = FirecrawlApp(api_key='fc-xxxxxxxxxxxxxxxx')

環境変数 FIRECRAWL_API_KEY を設定しておけば、引数なしで初期化できる。

export FIRECRAWL_API_KEY=fc-xxxxxxxxxxxxxxxx

# 環境変数から自動で読み込む
app = FirecrawlApp()

単一ページの取得(scrape)

まず1ページだけ。scrape_url にURLを渡すだけでいい。

result = app.scrape_url(
    'https://example.com/pricing',
    params={'formats': ['markdown', 'html']}
)

print(result['markdown'][:500])

返り値はこういう構造になる。

{
    'markdown': '# Pricing\n\nOur plans start at...',
    'html': '<h1>Pricing</h1><p>Our plans start at...</p>',
    'metadata': {
        'title': 'Pricing - Example',
        'description': 'Our pricing plans...',
        'language': 'en',
        'sourceURL': 'https://example.com/pricing',
        'statusCode': 200
    }
}

formats で取得形式を指定する。Markdownだけで足りるケースがほとんどだ。DOM構造まで必要ならhtmlも併せて取る。

JavaScriptで描画されるページも、デフォルトでブラウザ描画されるので特別な設定は要らない。ログインが必要なページは、headers でCookieを渡す。

result = app.scrape_url(
    'https://app.example.com/dashboard',
    params={
        'formats': ['markdown'],
        'headers': {
            'Cookie': 'session_id=abc123def456'
        }
    }
)

サイト全体のクロール(crawl)

本題はここ。サイトを丸ごと取る。crawl_url を使う。

crawl_result = app.crawl_url(
    'https://docs.example.com',
    params={
        'limit': 100,
        'scrapeOptions': {
            'formats': ['markdown']
        }
    },
    poll_interval=5
)

print(f"取得ページ数: {len(crawl_result['data'])}")
for page in crawl_result['data'][:3]:
    print(f"  - {page['metadata']['sourceURL']}")

出力例。

取得ページ数: 87
  - https://docs.example.com/
  - https://docs.example.com/getting-started
  - https://docs.example.com/api-reference

クロールの範囲は細かく制御できる。

crawl_result = app.crawl_url(
    'https://example.com',
    params={
        'limit': 200,
        'maxDepth': 3,
        'includePaths': ['/blog/*', '/docs/*'],
        'excludePaths': ['/admin/*', '/tag/*'],
        'allowBackwardLinks': False,
        'scrapeOptions': {
            'formats': ['markdown'],
            'onlyMainContent': True
        }
    }
)

onlyMainContent: True は地味だが効く。これを入れないと、全ページにヘッダーやフッター、サイドバーが重複して混ざる。AIに渡すデータが無駄にふくらむ原因になるので、最初から入れておくのがいい。

100ページを超えるサイトでは、同期的に完了を待つとタイムアウトの危険がある。非同期のAPIを使うほうが安全だ。

crawl_job = app.async_crawl_url(
    'https://large-site.example.com',
    params={'limit': 500}
)

job_id = crawl_job['id']
print(f"ジョブID: {job_id}")

import time

while True:
    status = app.check_crawl_status(job_id)
    completed = status.get('completed', 0)
    total = status.get('total', 0)
    print(f"進捗: {completed}/{total}")

    if status['status'] == 'completed':
        break
    time.sleep(10)

pages = status['data']
print(f"取得完了: {len(pages)}ページ")

AIで構造化データを抜き出す(extract)

Firecrawl v1で追加されたExtract機能を使うと、ページから必要な項目だけを構造化して取り出せる。取りたい形をスキーマで定義して渡す。

from pydantic import BaseModel
from typing import List, Optional

class Product(BaseModel):
    name: str
    price: Optional[str]
    description: str
    features: List[str]

result = app.scrape_url(
    'https://example.com/product/widget-pro',
    params={
        'formats': ['extract'],
        'extract': {
            'schema': Product.model_json_schema()
        }
    }
)

product = result['extract']
print(f"商品名: {product['name']}")
print(f"価格: {product['price']}")
print(f"特徴: {', '.join(product['features'])}")

出力例。

商品名: Widget Pro
価格: $49/month
特徴: リアルタイム同期, APIアクセス, カスタムダッシュボード

スキーマを渡さず、プロンプトで指示することもできる。

result = app.scrape_url(
    'https://example.com/about',
    params={
        'formats': ['extract'],
        'extract': {
            'prompt': '会社の設立年、従業員数、所在地を抽出してください'
        }
    }
)

競合30社の会社概要から、設立年と従業員数と所在地だけを一覧化する。そういう仕事が、これで一気に片づく。

自社でやるか、外部に頼むか

ここが経営判断の分かれ目になる。Firecrawlは登録すれば触れるが、「触れる」と「業務として回る」の間には距離がある。判断軸を3つに絞る。

社内にPythonを書ける人がいて、しかもその人の時間が空いているか。ここが一番大きい。上のコードを見て「これなら書ける」と思う人が社内にいるなら、無料枠で試して、そのまま内製に進むのが一番安い。逆に、コードを書ける人が本業で手一杯なら、片手間の内製は途中で止まる。止まった自動化は誰も直さないまま放置される。

一度きりか、繰り返すか。競合を一回だけ調べたいなら、内製でも外注でも大差ない。むしろ外注のほうが早い。毎週・毎月データを取り続けて、AIに食わせて、業務に組み込む。そこまで育てるなら、誰かが継続的に面倒を見る前提の設計が要る。この設計を最初に間違えると、後で作り直しになる。

取るデータに個人情報や機微な情報が混ざるか。顧客データや社内の非公開情報を扱うなら、データをどこに置くか、誰がアクセスできるかの設計が先に必要になる。ここは「動けばいい」で進めると事故る領域だ。SaaS版に外部送信していいのか、OSS版を自社内で閉じて動かすべきか、の判断が絡む。

ざっくり言うと、社内に手の空いたエンジニアがいる一度きりの調査なら内製。継続運用や、機微なデータや、業務への組み込みが絡むなら、設計だけでも外部の目を入れたほうが結局は安い。

導入の費用と期間の目安

金額と期間の感覚を持っておくと、社内で話が進めやすい。

ツール自体の費用は、上の料金表のとおり。試すだけなら無料、小規模運用でHobbyの$16、本格運用でStandardの$83が目安になる。ここは大きな金額ではない。効いてくるのは、動かす人の時間のほうだ。

期間の目安は用途で変わる。1ページ試して手応えを確かめるだけなら、その日のうち。競合サイトを丸ごと取ってデータにするような一回きりの調査なら、数時間から1日。毎週データを取り続けて業務に組み込む仕組みまで作るなら、設計とテストを含めて数日から数週間を見ておく。

注意したいのは、一番時間を食うのが「Firecrawlを動かす部分」ではないことだ。取ったデータをどう使うか、どこに貯めるか、誰がメンテナンスするか。この周辺設計のほうが手間になる。ツールが安く動くからといって、プロジェクト全体が安く済むわけではない。この見誤りが、次の失敗パターンにつながる。

よくある失敗パターン

私が実際にぶつかった、あるいは踏みかけたものを挙げる。

無料枠を初日で使い切る。limit を設定せずにクロールを走らせると、リンクをたどれるだけたどってしまう。テスト段階で500クレジットが一瞬で溶ける。最初は limit: 10 で動作確認して、様子を見ながら増やすのが無難だ。

取れると思ったページが取れない。Firecrawlはデフォルトで robots.txt に従う。相手サイトが robots.txt でブロックしているパスは取得できない。自社サイトのデータ移行で使うなら、一時的に自社の robots.txt を調整する必要が出ることもある。

レート制限で詰まる。無料プランは1分あたり10リクエストの上限がある。大量のページを取るときは、scrape_url をループで回すより、crawl_url で一括取得したほうがいい。クロール機能は内部でレート制限をうまく管理してくれる。

法的な確認を飛ばす。ここが一番痛い失敗になりうる。robots.txt を無視する設定にしたり、商用サイトを利用規約を確認せずにスクレイピングしたりすると、法的リスクを負う。競合分析でよそのサイトを取る前に、そのサイトの利用規約を必ず確認する。この確認を「たぶん大丈夫」で飛ばさない。

作ったが誰も使わない。技術的に動くものを作っても、業務のどこで誰がその出力を使うかが決まっていないと、そのまま放置される。ツールを動かす前に、取ったデータを何の判断に使うのかを先に決めておく。

Scrapy・Playwrightとの使い分け

Firecrawlが常に最適というわけではない。用途で使い分ける。

要件

向いているツール

細かいパーサーのカスタマイズが必要

Scrapy

ブラウザ操作(ログイン、クリック等)が必要

Playwright

サイト全体をMarkdownで一括取得したい

Firecrawl

AIに渡す構造化データが欲しい

Firecrawl(Extract)

無料で大量ページを取得したい

Scrapy(自己管理)

Firecrawlの強みは「とにかく早く、きれいなデータが欲しい」場面にある。パーサーを書かなくていいぶん、試作や検証のスピードが上がる。本番のデータパイプラインに組み込むなら、コストとレート制限を見て判断する。

これを自社に入れるとどうなるか

冒頭の話に戻る。競合30社のサービスページを集める仕事が、数日から数時間になった。この「時間の縮み方」が、Firecrawlが自社にもたらす一番わかりやすい変化だ。

具体的には、こういう場面で効く。

  • 競合の価格やサービス内容を定期的に一覧化して、自社の立ち位置を把握する
  • 旧サイトから新サイトへ、数百ページの記事をまとめて移す
  • 社内マニュアルや過去資料をデータ化して、問い合わせ対応AIの土台にする

どれも「人手でやると数日、放置すると誰もやらない」タイプの仕事だ。そこを仕組みで片づけると、担当者はもっと判断が要る仕事に時間を回せる。

ただし、ここまで読んでわかるとおり、ツールが動くことと業務が回ることは別だ。何のデータを、どう使い、誰が維持するのか。この設計を外すと、せっかく作った仕組みが止まる。

自社のどの業務にこれが効きそうか、内製と外注どちらで進めるのが現実的か。そのあたりを一度整理したいなら、まず無料の現在地診断(6問・約1分)をどうぞ(f2t.jp/diagnosis)。売り込みではなく、「そもそも自動化すべき業務か」の当たりを付けるところから。今のやり方のまま人手で続けるほうが安い、という結論になることもある。


この記事を書いた人

Tomo(F2T)

AIエージェント組織を自分の業務で毎日動かしている実装者。このブログの記事は、すべてその実作業の記録から生まれています。

WORKFLOW AUTOMATION

この記事のテーマに合うサービス:業務フロー自動化

スプレッドシート・メール・Slackの往復を、自動化で終わらせる

関連記事