Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

You can run browser automation from a serverless function, but the function platform does not automatically provide a full browser. Treat the function as the request or job handler and provide the browser separately: connect to a managed remote browser, or package and operate Chromium with the function. For one-off screenshots, PDFs, or rendered-page reads, a stateless browser API is usually the simplest fit; for multi-step interactions, use a live browser session. Package a browser yourself only when the control or economics justify the extra deployment and maintenance work.

Choose the browser architecture before writing the function

A serverless function can receive an HTTP request, validate it, start a job, and return or store a result. Browser automation still requires a browser runtime capable of loading and rendering the page. That runtime may be on a provider-managed browser pool or packaged alongside your function. A Lambda Function URL, API Gateway, or Worker is an entry point, not a guarantee that Chromium is installed.

Use a one-request browser action for simple jobs

For a single screenshot, PDF, or rendered-page extraction, use a stateless action where one request starts the task and returns the result. Cloudflare recommends Quick Actions for this kind of work; they are available through its REST API or from a Worker using a browser binding. See Cloudflare Browser Run and its getting-started guide.

Use a live session for scripted workflows

If the task must log in, click through several pages, retain cookies, or inspect changing state, connect Playwright or another supported client to a browser session. The function can control a remote browser over a provider-specific protocol. Decide how long the session lives, whether it can be reused, and how it is isolated from other jobs.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Package Chromium only for a reason

Bundling Chromium into a function image or layer gives you more control over the runtime, but you own compatible browser binaries, package size, startup behavior, and updates. Browserless published a Lambda packaging tutorial on April 29, 2024; it is illustrative vendor guidance, not a current AWS limits reference. Check current AWS limits and compatible package instructions before adopting it: Browserless: How to Deploy Playwright on AWS Lambda.

Decide between managed and packaged browsers

Question Managed browser Packaged browser
Who operates Chromium? The browser provider operates the remote pool; you configure the connection and manage your workflow. You build and maintain the browser package with the function.
Best task fit One-off actions or scripted sessions, depending on the provider’s API. Workloads requiring runtime control that a managed service does not provide.
Protocol and feature fit Verify the service’s REST, CDP, or Playwright-native support and required features. Verify the bundled browser version and automation library work together.
Capacity and cost Check browser concurrency, launch and request limits, session behavior, and browser-time charges. Check function concurrency, duration, memory, storage, and the engineering cost of packaging.
Latency and geography Measure from the function’s region to the browser location and target site. Measure in the function’s deployment region against the actual target workload.

Do not choose from an assumed speed or cost advantage: the available documentation does not establish a comparable cross-provider benchmark or current numerical price comparison. Include function compute, browser time, storage, egress, reuse or idle time, and maintenance in your own cost model.

Run a browser action in Cloudflare Workers

Cloudflare calls the service Browser Run; older references may call it Browser Rendering. Its documentation says Browser Run is available on Free and Paid plans. For a Worker, declare a browser binding, then call a Quick Action. The following minimal configuration illustrates the binding and the required compatibility date for Quick Actions.

Declare the binding

In wrangler.toml, use a compatibility date of 2026-03-24 or later for Quick Actions and declare the browser binding. Cloudflare’s current Wrangler reference says a Browser Run Worker must declare a browser binding. Compatibility dates from 2026-08-04 enable nodejs_compat and nodejs_compat_v2 by default; earlier dates need the compatibility flag opted in if your Worker requires it. Check the Wrangler reference for the current configuration details.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
name = "browser-job"
main = "src/index.js"
compatibility_date = "2026-08-04"

[browser]
binding = "BROWSER"

Call a Quick Action from the Worker

This example accepts a URL and asks the binding for a screenshot. Validate and restrict accepted URLs in a real service; otherwise your endpoint can be abused to make requests to arbitrary destinations. Quick Actions require remote mode while developing locally.

export default {
  async fetch(request, env) {
    const url = new URL(request.url).searchParams.get("url");
    if (!url) return new Response("Missing url parameter", { status: 400 });

    const result = await env.BROWSER.quickAction("screenshot", { url });
    return new Response(result, {
      headers: { "content-type": "image/png" },
    });
  },
};

Deploy with Wrangler after configuring the binding. Cloudflare’s Quick Actions compatibility requirement is a separate concern from the later Wrangler compatibility defaults: set a date that satisfies the Quick Actions minimum, then follow the binding and compatibility settings documented for your Worker. For longer workflows, use a browser session rather than stretching a single action into a stateful automation system. Cloudflare describes Durable Objects for preserving reusable browser sessions, Queues for asynchronous jobs, and object storage for archiving outputs.

Respect plan-specific limits

Cloudflare’s August 20, 2026 changelog says Workers Paid defaults became 200 concurrent browsers, three new browser instances per second, and 30 Quick Actions requests per second; it also says higher limits can be requested. These figures are Workers Paid defaults, not Free-plan limits or universal limits for other providers. Review the Browser Run changelog and your account’s applicable quota before setting concurrency.

Connect an external function to a managed browser

A function on another platform can call a remote browser service. Browserless is one example; its connection method depends on whether you need CDP or Playwright’s native protocol. Obtain the endpoint and token from your provider’s account, store credentials as secrets, and do not place them in a public client or source repository.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Browserless CDP with Playwright

Browserless’s default endpoint speaks Chrome DevTools Protocol (CDP), which Playwright can connect to with connectOverCDP. The endpoint URL format and authentication are provider-specific; use the exact endpoint issued for your account.

import { chromium } from "playwright";

export async function handler() {
  const browser = await chromium.connectOverCDP(process.env.BROWSERLESS_ENDPOINT);
  try {
    const context = await browser.newContext();
    const page = await context.newPage();
    await page.goto("https://example.com", { waitUntil: "domcontentloaded" });
    const title = await page.title();
    await context.close();
    return { statusCode: 200, body: JSON.stringify({ title }) };
  } finally {
    await browser.close();
  }
}

This example assumes the function runtime can load the Playwright package and has BROWSERLESS_ENDPOINT configured. It closes the context and browser connection in a finally block so a failed navigation does not skip cleanup. Browserless says remote browser use avoids downloading local browser binaries.

When to use the Playwright-native endpoint

Browserless documents a separate /playwright endpoint for Playwright-native connect(). Its vendor guidance says to use that mode for features such as page.route(), APIRequestContext, and non-Chromium browser support; native mode is coupled to the endpoint’s Playwright version. Check the vendor’s current Playwright connection documentation and align client and endpoint versions as directed. Do not assume CDP supports every Playwright capability.

Automated tests and parallel workers

For Playwright Test, Browserless recommends a worker-scoped fixture. Each parallel test worker opens a browser session and counts against plan concurrency. Size test parallelism to the account limit and ensure sessions are closed even when tests fail. For a single stateless task, a Quick Action or equivalent browser API can be simpler than managing test-style sessions.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Use Lambda as the handler, not as proof of browser availability

A Lambda Function URL can expose a function through an HTTP(S) endpoint for browsers and HTTP clients; API Gateway can also provide an entry point for serverless APIs. Neither means that Chromium is preinstalled. AWS describes these entry-point options in its Lambda Function URLs documentation and API Gateway integration guide.

For browser work on Lambda, either package a compatible browser and automation library in the function deployment or have the function connect to a remote browser pool. The first path requires checking current AWS package, architecture, timeout, memory, and storage constraints. The available packaging example is Browserless’s April 2024 vendor tutorial, so do not treat its package details as current AWS limits. The remote-pool path reduces local browser packaging, but adds a network connection and service-specific concurrency, protocol, region, and billing considerations.

Deploy browser jobs with bounded work and controlled access

Browser automation can consume substantial time and resources, and the target page is outside your function’s control. Design for a page that is slow, malformed, unavailable, or unexpectedly interactive.

  • Validate destinations. Allow only expected URL schemes and, where practical, an allowlist of hosts. This reduces the risk of your endpoint being used to access internal services or arbitrary third-party sites.
  • Set bounded navigation and job timeouts. Choose limits for navigation, action steps, and the whole function invocation. Return a useful timeout result instead of leaving work unbounded.
  • Limit concurrency and rate. Keep simultaneous jobs within both function capacity and browser-provider quotas. Apply backpressure or queue work when demand exceeds the safe rate.
  • Retry selectively. Retry transient connection failures with a small bounded policy; avoid blindly repeating actions that submit forms, make purchases, or otherwise have side effects.
  • Clean up sessions. Close contexts and browser connections in success and error paths. If sessions are deliberately reused, define isolation, expiry, and cleanup behavior.
  • Protect credentials and output. Keep browser tokens and target-site credentials in a secrets manager. Set access controls and retention rules for screenshots, PDFs, cookies, logs, and archived browser output.
  • Log actionable details. Record a job identifier, duration, result status, and provider error category without logging secrets or sensitive page content.

These are engineering safeguards, not a universal provider configuration: exact quota controls, retention options, and session semantics vary by service and should be checked against its documentation.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Troubleshoot common failures

  • “Browser is not defined” or binding unavailable: Check that the Worker declares the browser binding and that the binding name in code matches the configuration.
  • Quick Action rejected or unsupported: Confirm the Worker compatibility date is at least 2026-03-24, and use remote mode for local Quick Actions development.
  • Node compatibility behavior differs: Check the Worker’s compatibility date. Dates from 2026-08-04 enable the documented Node compatibility flags by default; earlier dates may require an explicit flag.
  • CDP connection fails: Verify the full provider endpoint, its authentication token, network egress, and that you are using the CDP connection method for a CDP endpoint. Do not send native Playwright connect() to the default CDP endpoint.
  • A Playwright feature is missing: Check protocol support. Browserless directs users to its Playwright-native endpoint for page.route(), APIRequestContext, or non-Chromium support, and requires attention to Playwright version compatibility.
  • Sessions are rejected under load: Reduce parallel workers or job concurrency, and compare demand with the service’s account limits and launch-rate quotas. For Cloudflare Paid, use the cited defaults only for that plan and date.
  • Lambda package fails to launch: Check browser binary compatibility with the function architecture and packaging layout, plus current memory, storage, and timeout limits. An older tutorial may no longer match current platform constraints.
  • Function times out on a slow page: Bound navigation and total work, identify whether the delay is in the target site or remote browser connection, and use a queued job for work that should not fit a synchronous request.

Or skip the browser setup

If the job is simply to produce a website screenshot, ScreenshotNeo offers a one-request screenshot API and MCP server. It accepts a URL and returns PNG, JPEG, WebP, or PDF output. Cookie banners and consent overlays, newsletter popups, and chat widgets are removed before capture; those cleanup steps can be turned off. Bot checks and CAPTCHAs, blank pages, timeouts, failed loads, and cache hits are not billed, and the response indicates the page verdict and billing status in headers.

For a direct call, see the ScreenshotNeo API documentation:

curl -G "https://api.screenshotneo.com/v1/shot" 
  -d access_key=YOUR_API_KEY 
  --data-urlencode url=https://example.com 
  -o shot.webp

ScreenshotNeo also has an MCP server with take_screenshot, get_page_info, and capture_pdf tools for Claude, Cursor, and other MCP clients. The free plan includes 1,000 screenshots per month without a card; paid plans start at $5 for 3,000 screenshots. Try it with the free ScreenshotNeo sign-up.

Frequently Asked Questions

Does a serverless function include a browser automatically?

No. A function needs a browser runtime, either packaged with it or provided by a remote browser service.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Can an AI agent control a browser through a screenshot API?

A screenshot API returns captures, while interactive control requires a session-capable browser interface or an agent tool designed for browser operations.

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.