この記事の対象読者
- Webスクレイピングで「Just a moment...」に阻まれたことがある人
- Cloudflare対策の選択肢を整理したい人
- 有料サービスを使わずに自前で対策したい人
2026年現在のCloudflareの壁
Webスクレイピングをしていると、ある日突然こんなHTMLが返ってくることがあります。
<title>Just a moment...</title>
<script>window._cf_chl_opt = { ... }</script>
Cloudflareの Managed Challenge です。HTTPステータスは200で返ってくるので、コード上は「成功」に見える。しかし中身はJavaScriptチャレンジページで、実際のコンテンツは一切含まれていません。
厄介なのは以下の点です。
- HTTPステータス200で返る → エラーハンドリングで捕捉できない
- JavaScript実行が必須 → requests/axios等のHTTPクライアントでは突破不可能
- ブラウザ自動化を検知 → 単純なPuppeteer/Playwrightも検知される
- IP評価 → データセンターIPは住宅用IPより厳しく判定される
2026年時点で、Cloudflareは以下を総合的に評価しています。
| 検査項目 | 内容 |
|---|---|
| TLSフィンガープリント | ブラウザ固有のTLS署名と一致するか |
| ブラウザフィンガープリント | Canvas、WebGL、AudioContext等 |
| JavaScriptチャレンジ | 所定の計算を正しく実行できるか |
| 行動分析 | マウス移動、クリックパターン |
| IPレピュテーション | データセンターIPか住宅用IPか |
対策の選択肢と比較
1. User-Agent偽装だけ
headers = {"User-Agent": "Mozilla/5.0 ..."}
requests.get(url, headers=headers)
効果: ほぼなし。 TLSフィンガープリントで即バレます。HTTPクライアントのTLS署名はブラウザと全く異なるため、ヘッダーをいくら偽装しても意味がありません。
2. Playwright/Puppeteer(素の状態)
const browser = await chromium.launch({ headless: true });
const page = await browser.newPage();
await page.goto(url);
効果: 低〜中。 JavaScriptは実行できますが、navigator.webdriver が true になる等、ヘッドレスブラウザの痕跡が多数残ります。Cloudflareはこれを検知します。
3. Playwright + Stealth Plugin
const { chromium } = require("playwright-extra");
const StealthPlugin = require("puppeteer-extra-plugin-stealth");
chromium.use(StealthPlugin());
効果: 中〜高。 navigator.webdriver の隠蔽、プラグイン偽装、WebGL/Canvas指紋の調整等を自動で行います。Managed Challengeレベルであれば多くのサイトで突破可能です。
4. Residential Proxy + ブラウザ自動化
効果: 高。 IPレピュテーションの問題を根本解決します。ただし月額コストが発生します($1.40〜$7/GB程度)。データセンターIPでどうしても通らないサイトへの最終手段。
5. 有料バイパスサービス
Bright Data Web Unlocker、ScrapFly、ZenRows等。
効果: 最高。 しかし月額$50〜$500+で、個人開発には厳しい価格帯。
6. FlareSolverr(セルフホスト)
効果: 低(2026年時点)。 かつては有効でしたが、Cloudflareの検知が進化し、2026年現在では多くのサイトで機能しません。
比較表
| 方法 | 効果 | コスト | 実装難易度 |
|---|---|---|---|
| User-Agent偽装 | ✗ | 無料 | 低 |
| 素のPlaywright | △ | 無料 | 低 |
| Playwright + Stealth | ○ | 無料 | 中 |
| Residential Proxy | ○ | 月$3〜 | 中 |
| 有料バイパスサービス | ◎ | 月$50〜 | 低 |
| FlareSolverr | △ | 無料 | 中 |
私のアプローチ: Cheerio → 自動検知 → Playwright切替
個人で運用しているWebスクレイピングAPIで、以下のアプローチを実装しました。
アーキテクチャ
リクエスト
↓
Phase 1: 通常のHTTPリクエスト(Cheerio)で取得 [高速: 1〜3秒]
↓
レスポンスHTML内にCloudflareマーカーを検知?
↓ No ↓ Yes
そのまま返却 Phase 2: Playwright + Stealth で再取得 [15〜35秒]
↓
チャレンジ自動待機 → 実コンテンツ取得
ポイントは Phase 1で高速に取得を試み、Cloudflareだった場合のみPlaywrightにフォールバック する点です。非保護サイト(大多数)は1〜3秒で処理され、Playwright起動のオーバーヘッドがかかりません。
実装の詳細について
バイパス手法の具体的なコード(検知マーカー、待機ロジック、ステルス設定の詳細)は 公開を控えます。
理由は明確で、手法を詳細に公開するとCloudflare側が対策を追加し、イタチごっこが加速するためです。すでにpuppeteer-extra-plugin-stealthのソースコードは公開されており、Cloudflareのエンジニアも把握しているでしょう。個別のバイパステクニックを広めることは、長期的にはスクレイピングコミュニティ全体にとってマイナスです。
概要レベルで言えば:
- Playwright + Stealth Pluginをベースに追加の独自対策を施している
- チャレンジページの自動検知と動的な待機処理
- 成功時のセッション情報の永続化(2回目以降高速)
- ヒューマンライクな振る舞いのシミュレーション
正直に書く: できないこと
- IPレベルのブロック — サイト運営者がデータセンターIPレンジ自体をブロックしている場合、技術的な回避は不可能です。Residential Proxyが必要になります。(現在未対応)
- 明示的なCAPTCHA(Turnstile) — バックグラウンドで自動解決されるManaged Challengeのみ対応。ユーザー操作を要求するCAPTCHAには未対応です。
実測データ
データセンターIP(Railway)からの実測結果です。
Cloudflare保護サイト
| サイト | チャレンジ種別 | 結果 | 所要時間 |
|---|---|---|---|
| nopecha.com(CFデモ) | Managed Challenge | 突破 | 33秒 |
| nowsecure.nl(CF検証) | JS Challenge | 突破 | 18秒 |
| メルカリ | CF保護 | 突破 | 34秒 |
| Medium | CF保護 | 突破 | 17秒 |
| DoorDash | CF保護 | 突破 | 18秒 |
5サイト中5サイトで突破成功(100%)。
非Cloudflareサイト(通常処理)
| サイト | エンジン | 所要時間 |
|---|---|---|
| カーセンサー | Cheerio | 2秒 |
| SUUMO | Cheerio | 2秒 |
| goo-net | Cheerio | 3秒 |
| 健美家 | Cheerio | 1秒 |
非保護サイトはPlaywrightを起動せず、高速なCheerioで処理されます。
性能特性まとめ
| 条件 | 所要時間 |
|---|---|
| 非Cloudflareサイト | 1〜3秒 |
| Cloudflareサイト(初回) | 15〜35秒 |
| Cloudflareサイト(セッション再利用) | 3〜10秒 |
学んだこと
1. HTTPステータス200の罠
Cloudflareのチャレンジページはステータス200で返ります。「Cheerioが失敗したらPlaywrightにフォールバック」という単純な設計では、チャレンジページを「成功」と判定してしまいます。レスポンスの中身を検査する処理が必須です。
2. headless: "new" の互換性問題
Chromiumの新しいヘッドレスモード(headless: "new")はヘッド付きブラウザと同等のフィンガープリントを持つとされています。有望に思えましたが、playwright-extraとの互換性がなく、ブラウザが起動しなくなりました。新しい技術を導入する際は必ず既存スタックとの互換性テストが必要です。
3. Cloudflare ≠ サイト独自WAF
Cloudflareのチャレンジを突破しても、その先でサイト独自のWAFが「アクセスができません」を返すケースがあります。これはCloudflareの問題ではなく、サイト運営者がIPレンジ単位でブロックしているパターンです。この場合はResidential Proxyが唯一の解決策です。
APIとして使う
上記の対策を組み込んだ WebReader AI API をRapidAPIで公開しています。URLを渡すだけで、Cloudflareの有無を意識せずにWebページをMarkdown/JSONで取得できます。
- WebReader AI API(RapidAPI) — 無料枠あり(100リクエスト/月)
- サンプルコード(GitHub) — Python / JavaScript / LangChain
クイックスタート
import os, requests
response = requests.get(
"https://webreader-ai.p.rapidapi.com/api/read",
headers={
"X-RapidAPI-Key": os.environ["RAPIDAPI_KEY"],
"X-RapidAPI-Host": "webreader-ai.p.rapidapi.com",
},
params={"url": "https://example.com", "output": "json"},
)
data = response.json()
print(data["content"]) # Markdown形式のコンテンツ
print(data["engine"]) # "cheerio" or "playwright"(自動選択)
engine フィールドで、Cloudflare検知によりPlaywrightに自動切替されたかどうかを確認できます。
まとめ
| やりたいこと | 推奨アプローチ |
|---|---|
| とにかく安くCloudflareを突破したい | Playwright + Stealth Plugin(無料) |
| 確実に突破したい | 上記 + Residential Proxy(月$3〜) |
| 自前実装したくない | 有料バイパスサービスまたはWebReader AI API |
| IPブロックも回避したい | Residential Proxy必須 |
Cloudflare対策は「これで完璧」という銀の弾丸はなく、サイトの保護レベルに応じた段階的なアプローチが必要です。まずは無料のStealth Pluginで試し、通らなければProxyの導入を検討する、という段階的な戦略が現実的です。
スクレイピングは各サイトの利用規約とrobots.txtに従い、過度な負荷をかけないように行いましょう。