ScreenshotNeo

BlogHow-to

How to Handle Cloudflare with Playwright

Identify which Cloudflare check Playwright encountered, then use supported workflows for testing Turnstile, automating your own site, or troubleshooting access.

By the ScreenshotNeo team4 October 20269 min read

Short answer: Playwright is not a supported way to solve Cloudflare production challenges. First identify what Cloudflare presented: a Challenge Page, a Turnstile widget, JavaScript Detections, or another security action. If you own the application, use Turnstile’s documented test keys or configure an authorized test path on your Cloudflare zone. If a third-party site challenges your automation, do not try to defeat the challenge; use the site’s supported access method or contact its owner.

This guide covers the supported path for each situation, how to diagnose a challenge loop as a legitimate visitor, and what to configure when you control the site. It does not provide a production challenge bypass.

1. Choose the workflow that matches your situation

Your situation Supported next step
You are testing your own app’s Turnstile integration Use Cloudflare’s documented Turnstile test keys in the test environment. Keep test credentials and behavior separate from production.
You are automating a site or zone you control Use an authorized test configuration or Cloudflare’s documented Browser Run integration. Configure any required access rules at the zone or application layer.
A third-party production site presents a Cloudflare challenge Use an ordinary supported browser, resolve legitimate browser or network problems, and ask the site owner for an approved automation or data-access route.

Cloudflare explicitly says browser automation frameworks, including Playwright, are not supported for solving production challenges. A different user-agent string or Playwright launch option does not turn challenge solving into a supported workflow. See Cloudflare’s supported-browser guidance.

2. Identify which Cloudflare mechanism you encountered

“Cloudflare blocked Playwright” is not a diagnosis. Different products and rules can produce a challenge or rejection, and the fix depends on the feature and whether you control the zone.

Mechanism What it means Where to investigate
Challenge Page A browser-interactive challenge interrupts the request flow. Challenge actions can be configured by WAF custom rules, rate-limiting or IP-access rules, Bot Management, Bot Fight Mode or Super Bot Fight Mode, HTTP DDoS protection, and Under Attack Mode. For your own zone, inspect the active security product and matching rule. For a third-party site, use the site’s supported route.
Turnstile An embedded widget used by an application to check a visitor or submission. It is related to the challenge mechanism but is an application integration, not a universal browser CAPTCHA. For an app you own, use the official test keys and validate the server-side verification flow.
JavaScript Detections An optional signal that runs without pausing the visitor to show a challenge. A rule can use the resulting signal as an input to a security decision. For your zone, check whether detection had an opportunity to run before applying a rule that depends on it.
Another WAF or Bot Management action A configured rule may block, log, or challenge a request based on multiple signals. Review the matched event and rule in your zone’s security configuration; do not assume every denial is a CAPTCHA.

Cloudflare describes multiple detection engines, including request heuristics, JavaScript Detections, and machine-learning scoring on eligible plans. Its Bot Score runs from 1 to 99; that is a product scoring scale, not a universal threshold for challenging Playwright. No single user-agent value or Playwright setting guarantees a particular outcome. See How Challenges work and Bot detection engines.

3. Test a Turnstile integration you own

Use Cloudflare’s test keys when testing your application’s Turnstile integration. They are intended for development and automated tests; do not substitute a production widget or attempt to make Playwright solve a real visitor challenge. Keep your application’s normal server-side token verification in the test flow so that the integration is exercised end to end.

A minimal Playwright test can submit the form using the test configuration supported by your app. The page selectors and route below are examples you must adapt to your application; the test key itself should come from Cloudflare’s official Turnstile testing documentation, not a production site.

import { test, expect } from '@playwright/test';

test('submits the form with Turnstile test configuration', async ({ page }) => {
  await page.goto('http://localhost:3000/contact');
  await page.getByLabel('Email').fill('developer@example.test');
  await page.getByLabel('Message').fill('Turnstile integration test');

  // Configure the application under test with Cloudflare's documented
  // Turnstile test site key and matching server-side test verification.
  await page.getByRole('button', { name: 'Send' }).click();
  await expect(page.getByText('Message sent')).toBeVisible();
});

Replace the sample URL, labels, expected result, and test configuration with your app’s actual values. Cloudflare publishes test keys and their expected behavior in its Turnstile testing documentation. Never embed a production secret in browser-side test code.

4. Run Playwright against a site you control

If the target is your own Cloudflare-protected site, first decide whether the test needs to exercise Cloudflare itself. For ordinary application UI tests, a dedicated test hostname or a narrowly scoped server-side rule can keep the test reliable. If the goal is to test Cloudflare behavior, keep the security policy active and assert the intended result. Any exception should be limited to an authorized test environment and managed by the site owner.

Use Cloudflare Browser Run when it fits

Cloudflare documents a Playwright integration for Browser Run. Follow its current setup guide for package installation and Worker configuration. The documented setup requires the nodejs_compat compatibility flag and a compatibility date of 2025-09-15 or later. Concurrent connections require @cloudflare/playwright version 1.3.0 or later. These are version-sensitive requirements; check the current Browser Run Playwright documentation before deploying.

Browser Run requests are always identified as a bot. Setting a custom user agent does not bypass bot protection. Use the integration for authorized automation of workflows you control, not to defeat a target site’s defenses.

Use a controlled test environment

  1. Create a test hostname or environment with data and credentials intended for automation.
  2. Decide whether the test should pass through Cloudflare security controls or exercise a documented test configuration.
  3. If you adjust a rule, scope it to the test environment and the minimum necessary traffic, then review the resulting security events.
  4. Keep production challenge behavior intact and validate production access through an approved route.

5. Troubleshoot a challenge as a legitimate visitor

If you are a human visitor who cannot complete a challenge in your normal browser, diagnose the browser and network without automating or spoofing the challenge.

  1. Update the browser. Use a current browser supported by Cloudflare’s challenge flow.
  2. Temporarily inspect extensions. Privacy, script-blocking, or fingerprint-modification extensions can block challenge scripts or alter user-agent, Canvas, or WebGL behavior. Test with extensions disabled only as a diagnostic step.
  3. Remove developer overrides. While diagnosing, clear DevTools network throttling, user-agent overrides, viewport overrides, and JavaScript disabling.
  4. Check the network path. A VPN, proxy, or changing network can cause the client IP to differ between the challenge and its completion request. Cloudflare warns that a solve request from a different IP can be invalid and cause a challenge loop.
  5. Retry in the ordinary browser environment. Avoid scripts or tools that alter browser fingerprints. If the challenge persists, give the site owner the time, page, and error details so they can inspect their configuration.

These checks help with legitimate browser failures. They do not make Playwright challenge solving supported.

6. Configure JavaScript Detections on a zone you own

JavaScript Detections does not pause the visitor for a challenge. Cloudflare injects its detection script on HTML requests, not AJAX requests, and at least one HTML request must occur before the signal is available. The documented signal is cf.bot_management.js_detection.passed.

  • Do not apply the signal to a visitor’s first request, before detection could run.
  • Do not apply it indiscriminately to APIs, native-app endpoints, or WebSockets.
  • For the documented enforcement scenario, Cloudflare recommends a Managed Challenge action because legitimate visitors may not have received the detection signal for browser or network reasons.
  • Check plan and product eligibility. The cited custom-rule procedure lists an Enterprise Bot Management subscription as a prerequisite.

Follow Cloudflare’s current JavaScript Detections documentation for rule syntax and eligibility. The documentation describes a 15-minute detection lifespan and reinjection before the session expires; verify current details when implementing a time-sensitive policy.

7. Troubleshooting common failures

Symptom Likely cause Action
Playwright repeatedly receives a challenge The site is applying a production challenge to automation, or a configured security rule is matching the request. For a third-party site, stop automation and request an approved access method. For your zone, inspect the matched rule and use a documented test setup.
Challenge page loops in a regular browser Challenge scripts are blocked or modified, browser overrides are active, or the client IP changes between challenge and completion. Update the browser, inspect extensions and DevTools overrides, use a consistent network path, then contact the site owner if it continues.
Turnstile test fails in CI The test uses production configuration, the app’s server verification does not match the test setup, or the form selectors/assertion are stale. Use Cloudflare’s test keys and documented expected behavior; verify the server-side test path and update selectors to match the app.
JavaScript Detection field is missing or false No eligible HTML request has allowed injection yet, the request is an API/native-app/WebSocket request, or the signal is unavailable for that visitor. Do not enforce it on the first request or unsuitable endpoints; use the documented rule pattern and a Managed Challenge where appropriate.
Browser Run setup reports compatibility or concurrency issues The Worker compatibility configuration or package version does not meet the current requirements. Check for nodejs_compat, compatibility date 2025-09-15 or later, and package version 1.3.0 or later for concurrent connections.
Custom user agent does not change the result Cloudflare evaluates more than the user-agent string; Browser Run is also identified as a bot. Do not treat user-agent changes as a bypass. Use owner-authorized configuration or an approved access route.

8. Performance, reliability, and cost considerations

Challenge behavior is a security decision involving configured products and request signals, so a test that relies on a third-party production challenge completing in automation is inherently fragile and unsupported. Make tests deterministic with documented test keys, a controlled environment, or Cloudflare’s supported integration where appropriate. If you own the zone, account for the fact that JavaScript Detections needs an HTML request before its signal is available. Browser Run’s compatibility and concurrency requirements can affect deployment design; check the current documentation for changes.

The research documentation does not establish a universal challenge rate, Playwright success rate, or threshold that predicts when a challenge will appear. Do not budget or design a production workflow around such a figure. For plans and eligibility tied to Cloudflare features, use the plan documentation for your account.

9. Or skip the browser setup

If your task is to capture a page screenshot, ScreenshotNeo is a website screenshot API and MCP server from Yorker Media. It is not a way to solve Cloudflare challenges; it returns the page verdict in response headers, and bot checks are not billed. See the ScreenshotNeo API documentation.

curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
import requests
r = requests.get("https://api.screenshotneo.com/v1/shot", params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"}, timeout=90)
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);

Before capture, ScreenshotNeo accepts cookie or consent banners like a visitor and removes more than 60 known consent platforms, newsletter popups, and chat widgets; each step can be turned off. Bot checks, CAPTCHAs, blank pages, timeouts, failed loads, and cache hits cost nothing, and response headers report the page verdict and billing status. Its MCP server provides take_screenshot, get_page_info, and capture_pdf for AI agents. The free plan includes 1,000 screenshots a month with no card; paid plans start at $5 for 3,000 screenshots. Every feature is on every plan.

Sign up for 1,000 free screenshots a month, with no card required.

FAQ

Can Playwright solve a Cloudflare challenge on a production website?

Cloudflare says automation frameworks such as Playwright are not supported for solving production challenges. Use the site’s normal visitor flow or request an approved automation route.

Is Turnstile the same as a Challenge Page?

They use the same underlying challenge mechanism, but Turnstile is an embedded application widget. For automated testing of an integration you own, use Cloudflare’s test keys.

Does JavaScript Detections show a CAPTCHA?

No. It is a signal feature that runs without pausing the visitor. A site can use its result as an input to a separate security rule.

Can a screenshot API access a page that blocks automation?

A screenshot API does not make a blocked request authorized or guarantee access. ScreenshotNeo reports page outcomes and does not bill bot checks or failed loads; use an approved route for protected content.

Sources