インターネット上の「Cloudflare を回避する方法」チュートリアルのほとんどは、2024 年後半に動作しなくなりました。理由は、Cloudflare が新しい防御を追加したからではありません。古い防御である JA3 フィンガープリントと基本的なヘッダーチェックが、あらゆる近道を破る新世代に置き換えられたからです。本ガイドは、Cloudflare が 2026 年に実際に何をチェックするのか、なぜ cloudscraper、undetected-chromedriver、そしてほとんどの「stealth」プラグインが失敗するのか、そして今なお本番で動く四層レシピを説明します。
率直なまとめを先に:単一のトリックは存在しません。Cloudflare を確実に回避するには、正しい IP、正しい TLS フィンガープリント、正しい HTTP/2 フレーム順序、そして(Bot Management ティアには)本物のブラウザが必要です。このうちどれか 1 つでも誤れば、リクエストが origin サーバーに届く前にエッジフィルターで失敗します。
Cloudflare の bot 検知は、エッジでのフィルターのパイプラインとして動きます。各リクエストは順番にそれらを通過します。最も早く拒否したフィルターが勝つので、リクエストはどんなフィンガープリントやヘッダーも検査される前に IP レピュテーションだけで失敗することがあります。
これは最初で最も安価なチェックです。Cloudflare は ASN(Autonomous System Number)でキー付けしたデータベースを保持しています。よく知られたクラウドプロバイダー(AWS AS16509、GCP AS15169、Azure AS8075、OVH AS16276、DigitalOcean AS14061、Hetzner AS24940、Vultr AS20473)に属する ASN は、最も厳しい精査を受けます。完璧なブラウザ級のフィンガープリントがあっても、これらの ASN から発したリクエストは、無罪が証明されるまで有罪として扱われます。
residential ASN(Comcast AS7922、Verizon AS701、China Telecom AS4134、BT AS2856)は正当と推定されます。不格好な Python フィンガープリントを持つ residential IP からのリクエストでも通ることがある一方で、完璧な Chrome フィンガープリントを持つ datacenter IP からのリクエストはチャレンジされるかブロックされます。
JA4 は、FoxIO がリリースした JA3 の 2023 年の後継です。特定の TLS ClientHello フィールドをハッシュ化します:TLS バージョン、暗号スイート(順序付き)、拡張(順序付き)、ALPN プロトコル、署名アルゴリズム、そしてサポートされるグループ。出力は t13d1516h2_8daaf6152771_b1ff8ab2d16f のような決定論的なフィンガープリントです。
本物の Chrome 124 は 1 つの特定の JA4 を生成します。本物の Firefox 124 は別のものを生成します。Python の requests ライブラリ(urllib3 と OpenSSL を使用)は、暗号順序と拡張リストが Chrome にも Firefox にも一致しないため、どんな本物のブラウザも決して出さない JA4 を生成します。Cloudflare は、どんな HTTP ヘッダーもパースする前にこのパターンにフラグを立てます。
含意:システムの OpenSSL や標準の Python TLS を使うすべてのライブラリは検知可能です。これには requests、aiohttp、httpx(デフォルト設定)、そしてそれらの上に構築されたあらゆる「bypass」ラッパーが含まれます。
HTTP/2 接続は settings フレーム、window updates、priority フレーム、headers フレームを運びます。ブラウザはこれらを特定の値とともに特定の順序で送ります。Chrome 124 はこれらの正確な値を持つ初期 SETTINGS フレームを送り、次に WINDOW_UPDATE、次に HEADERS を送ります。HTTP/2 を有効にした Python の httpx は異なる settings ペイロードを送り、Chrome が含める priority フレームをスキップします。
HTTP/2 の疑似ヘッダー順序もアイデンティティを漏らします。Chrome は :method、:authority、:scheme、:path をその順序で送ります。Firefox は :method、:path、:authority、:scheme を送ります。ほとんどの Python と Go のライブラリはこれらをアルファベット順にシリアライズします。Cloudflare は、宣言された User-Agent に期待されるパターンと順序を照合し、不一致にフラグを立てます。
HTTP/1.1 のヘッダーは挿入順を保持します。本物の Chrome はヘッダーを固定の順序で送ります:Host、Connection、Cache-Control、sec-ch-ua、sec-ch-ua-mobile、sec-ch-ua-platform、Upgrade-Insecure-Requests、User-Agent、Accept、Sec-Fetch-Site、Sec-Fetch-Mode、Sec-Fetch-User、Sec-Fetch-Dest、Accept-Encoding、Accept-Language。Python の requests はそれらを並べ替え、ときに大文字小文字を異なる形で付けます。手動で正しい順序にヘッダーを設定しても、下層のライブラリが再ソートするため役に立ちません。
先のフィルターを通過してもスコアがまだ疑わしい場合、Cloudflare は JavaScript チャレンジを返します。そのスクリプトはブラウザ環境の値(canvas ハッシュ、WebGL レンダラー、audio context、navigator プロパティ、タイミング計測)からトークンを計算し、XHR 経由で送信します。どんな HTTP クライアントもこれを解けません。本物のブラウザが必要で、そのブラウザは本物に見えなければなりません(navigator.webdriver = true なし、プロパティの欠落なし)。
Bot Management ティアでは、Cloudflare は継続的に実行されるスクリプトを通じてマウスの動き、スクロール速度、クリックのタイミング、キーストロークのダイナミクスを収集します。ページを読み込んで一度もマウスを動かさずに即座にスクレイプする headless ブラウザは、数秒以内に検知されます。本物のユーザーは不規則に動き、止まり、読み直します。bot は直線的にスクロールし、ピクセル単位で正確にクリックします。
2021–2024 年のスクレイピングを支えた近道ツールは、すべて 1 つの失敗モードを共有しています:可視の表面はパッチするが、下層の TLS スタックはパッチしません。
| ツール | 何をパッチするか | 2026 年になぜ失敗するか |
|---|---|---|
cloudscraper | JS チャレンジソルバー(レガシー) | Cloudflare は 2023 年に Turnstile へ移行;レガシーチャレンジは非推奨 |
undetected-chromedriver | Selenium のリークフラグをパッチ | JA4 が依然として下層の chromedriver の TLS から漏れる;navigator.webdriver は 40 以上のシグナルの 1 つにすぎない |
selenium-stealth | なりすました JS プロパティを注入 | Cloudflare は JS ではなく C++ 層から読む;なりすましは不整合として検知可能 |
FlareSolverr | 1 回限りのチャレンジ解決のために Chromium をラップ | cf_clearance がソルバーの IP に紐付く;新鮮なプロキシはトークンを即座に無効化する |
標準の puppeteer-extra-plugin-stealth | 約 17 の検知ポイントをパッチ | Cloudflare は 2024–2025 年にプラグインがカバーしない約 12 の新しいチェックを追加した |
パターンは明白です:本物のブラウザをラップして既知のリークをパッチするツールは、数ヶ月以内に軍拡競争に負けます。ブラウザの TLS スタックをシミュレートするツール(curl_cffi、tls-client)は、配線により近いところに位置するため生き延びてきました。
2026 年に動く回避には、四層すべてが必要です。どれか 1 つでもスキップすると、成功率は 1 桁に落ちます。
Cloudflare Pro 以上を運用するあらゆるサイトでは、これは交渉の余地がありません。IP レピュテーションフィルターは、TLS ハンドシェイクが完了する前に datacenter ASN を拒否します。cf_clearance cookie が生き残るよう、少なくとも 10 分間 sticky セッションを持つ residential プロキシを使ってください。
curl_cffi(Python)または tls-client(Go/Python)を使ってください。どちらも、Chrome の正確な暗号順序、拡張リスト、ALPN 値を備えた、改変された BoringSSL にリンクします。
from curl_cffi import requests
response = requests.get(
"https://target.com/api/products",
impersonate="chrome124",
proxies={"https": "http://user-session-abc123:[email protected]:10001"},
timeout=30,
)
print(response.status_code, len(response.text))
impersonate="chrome124" パラメータが TLS スタックを入れ替え、ClientHello が Chrome 124 とバイト単位で一致するようにします。JA4 ハッシュは本物の Chrome 124 のインストールと同一になります。residential プロキシと組み合わせれば、最初の 2 つのフィルターを通過します。
curl_cffi は impersonate を使うと自動的に Chrome の順序でヘッダーを設定します。カスタムヘッダーを追加するなら、途中に挿入するのではなく末尾に追加してください。本物の Chrome が送らないヘッダー(たとえば通常のナビゲーションでの X-Requested-With)の設定は避けてください。
Accept-Language については、プロキシの地理的位置に一致させてください。Accept-Language: zh-CN,zh;q=0.9 を送る US residential IP は、小さいながらも本物のシグナルです。US の IP には en-US,en;q=0.9、ドイツの IP には de-DE,de;q=0.9、といった具合に使ってください。これは無料で直せる数少ないシグナルの 1 つです。
ターゲットが Managed Challenge をトリガーする(レスポンスボディに CF のチャレンジページが見える)と、curl_cffi だけでは解けません。パッチした Chromium を使う Playwright に切り替えてください。
from playwright.sync_api import sync_playwright
from rebrowser_playwright.sync_api import sync_playwright as rebrowser_sync
with rebrowser_sync() as p:
browser = p.chromium.launch(
headless=True,
proxy={
"server": "http://gate.jibaoproxy.com:10001",
"username": "user-session-abc123",
"password": "pass",
},
)
context = browser.new_context(
user_agent="Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Safari/537.36",
viewport={"width": 1920, "height": 1080},
locale="en-US",
timezone_id="America/New_York",
)
page = context.new_page()
page.goto("https://target.com/", wait_until="networkidle")
# cf_clearance is now in context.cookies()
cookies = context.cookies()
cf_clearance = next((c for c in cookies if c["name"] == "cf_clearance"), None)
browser.close()
標準の playwright ではなく rebrowser-playwright を使ってください。これは、Cloudflare が headless 自動化を検知するために読む CDP ランタイムのリーク(Runtime.enable、CDP コマンドのページへの露出)をパッチします。チャレンジを通過したら、cookie から cf_clearance を抽出し、実際のスクレイピングループのために curl_cffi に渡し戻します。ブラウザはリクエストごとではなく、セッションごとに 1 回必要です。
最も安いプロキシを使おうという本能は、Cloudflare で保護されたサイトではほぼ常に間違いです。実際の数字で計算を追ってみましょう。
前提:平均 HTML ページ 500KB、合計 100,000 ページのスクレイピング、ターゲットは Bot Fight Mode を有効にした Cloudflare Pro を使用。
| 構成 | 帯域コスト | 成功率 | 成功あたりのリクエスト数 | 総コスト | ページあたりコスト |
|---|---|---|---|---|---|
| Datacenter $0.8/GB + requests | $0.0005 / req | 0.5% | 200 | $10,000 | $0.10 |
| Datacenter $0.8/GB + curl_cffi | $0.0005 / req | 3% | 33 | $1,650 | $0.0165 |
| Residential $2/GB + requests | $0.0033 / req | 40% | 2.5 | $825 | $0.0083 |
| Residential $2/GB + curl_cffi | $0.0033 / req | 92% | 1.09 | $360 | $0.0036 |
| Residential $2/GB + Playwright (rebrowser) | $0.017 / req (assets + JS) | 96% | 1.04 | $1,700 | $0.017 |
注目に値する 2 つの発見:
これは、Cloudflare で保護されたターゲットを大規模にスクレイプする顧客に当社が推奨するパターンです。Playwright の使用(遅くて高い)を最小化し、curl_cffi の使用(速くて安い)を最大化します。
from curl_cffi import requests as cf_requests
from rebrowser_playwright.sync_api import sync_playwright
PROXY_USER_FMT = "user-session-{sid}"
PROXY_HOST = "http://gate.jibaoproxy.com:10001"
PROXY_PASS = "your_password"
def get_cf_clearance(target_url, session_id):
"""One-shot Playwright call to solve the challenge and extract cf_clearance."""
with sync_playwright() as p:
browser = p.chromium.launch(
headless=True,
proxy={"server": PROXY_HOST,
"username": PROXY_USER_FMT.format(sid=session_id),
"password": PROXY_PASS},
)
ctx = browser.new_context(user_agent="Mozilla/5.0 ... Chrome/124.0.0.0 Safari/537.36")
page = ctx.new_page()
page.goto(target_url, wait_until="networkidle", timeout=45000)
cookies = ctx.cookies()
browser.close()
return {c["name"]: c["value"] for c in cookies}
def scrape_with_clearance(urls, session_id, cookies):
"""Reuse the same session_id (sticky IP) for all requests."""
proxy = f"http://{PROXY_USER_FMT.format(sid=session_id)}:{PROXY_PASS}@gate.jibaoproxy.com:10001"
out = []
for url in urls:
r = cf_requests.get(
url,
impersonate="chrome124",
proxies={"https": proxy},
cookies=cookies,
timeout=30,
)
if r.status_code == 200:
out.append((url, r.text))
elif r.status_code in (403, 503) and "challenge" in r.text.lower():
# cf_clearance expired; re-solve
cookies = get_cf_clearance(url, session_id)
r = cf_requests.get(url, impersonate="chrome124",
proxies={"https": proxy}, cookies=cookies)
out.append((url, r.text))
return out, cookies
# Usage
session_id = "scrape-job-2026-05-27"
cookies = get_cf_clearance("https://target.com/", session_id)
results, cookies = scrape_with_clearance(target_urls, session_id, cookies)
このレシピのキーポイント:
一部の Cloudflare デプロイメントは、どんな妥当なコストでも回避できません。これらのシグナルが見えたら、決して安定しない回避に予算を燃やす代わりに、戦略を切り替えてください(API を使う、サイトオーナーと提携する、データを買う)。
| ターゲットティア | レシピ | 期待される成功率 |
|---|---|---|
| CF Free / Pro(Bot Fight なし) | Datacenter + curl_cffi | 60–75% |
| CF Free / Pro + Bot Fight Mode | Residential + curl_cffi | 85–93% |
| CF Business | Residential + curl_cffi + 時折 Playwright | 80–90% |
| CF Business + Turnstile | Residential + rebrowser-playwright(毎リクエスト) | 70–85% |
| CF Enterprise + Bot Management | Mobile residential + rebrowser + 行動シミュレーション | 30–60% |
| CF Enterprise + Bot Management + カスタム WAF | スクレイプしない;API か提携を追う | <10% |
JIBAO Proxy は、240 以上の国にまたがる 9,000 万以上の IP、最大 60 分の sticky セッション、$2/GB から始まる国レベルのターゲティングを備えたダイナミック residential プロキシを提供します。mobile IP についてはダイナミック mobile プロキシを参照。どちらも curl_cffi、tls-client、Playwright、Puppeteer、Selenium、そして HTTP/SOCKS5 プロキシをサポートするあらゆる HTTP クライアントですぐに動きます。
関連記事:Sticky vs Rotating プロキシセッションはセッション設定を詳しく扱います。AI Agent 向けプロキシは、Cloudflare 回避ワークフローと大きく重なる AI agent のユースケースを説明します。
500MB の無料トラフィックを手に入れましょう。コミットする前に、curl_cffi + sticky residential の組み合わせをあなたのターゲットで試してください。
無料トライアルを開始新規ユーザーは登録時に500MBを獲得、さらに初回チャージにボーナスが付きます。期間限定オファーです。