For AI agents: a documentation index is available at /llms.txt
Skip to main content

Screenshot API

Capture PNG, JPEG, or WebP screenshots of a page. Pass Puppeteer-style settings through the options object.

Endpoint

  • Method: POST
  • Path: /screenshot
  • Auth: token query parameter (?token=)
  • Content-Type: application/json
  • Response: image/png (or image/jpeg, image/webp based on options.type)

See the OpenAPI reference for complete details.

Prerequisites

Quickstart

curl -X POST \
"https://production-sfo.browserless.io/screenshot?token=YOUR_API_TOKEN_HERE" \
-H 'Cache-Control: no-cache' \
-H 'Content-Type: application/json' \
-d '{
"url": "https://example.com/",
"options": {
"fullPage": true,
"type": "png"
}
}' \
--output "screenshot.png"

Response

HTTP/1.1 200 OK
Content-Type: image/png

<binary>

Examples

Setting HTML content

Use the html field to render inline HTML instead of navigating to a URL.

danger

When you send html, do not include url in the same request.

curl -X POST \
"https://production-sfo.browserless.io/screenshot?token=YOUR_API_TOKEN_HERE" \
-H 'Cache-Control: no-cache' \
-H 'Content-Type: application/json' \
-d '{
"html": "<html><body><h1>Hello World!</h1></body></html>",
"options": {
"fullPage": true,
"type": "png"
}
}' \
--output "screenshot.png"

Adding custom styles and scripts

Use addScriptTag and addStyleTag to inject scripts and styles before the screenshot is taken.

curl -X POST \
"https://production-sfo.browserless.io/screenshot?token=YOUR_API_TOKEN_HERE" \
-H 'Cache-Control: no-cache' \
-H 'Content-Type: application/json' \
-d '{
"url": "https://example.com/",
"addScriptTag": [
{ "url": "https://code.jquery.com/jquery-3.7.1.min.js" },
{ "content": "document.querySelector(`h1`).innerText = `Hello Word!`" }
],
"addStyleTag": [
{
"content": "body { height: 100vh; background: linear-gradient(45deg, #da5a44, #a32784); }"
},
{
"url": "https://interactive-examples.mdn.mozilla.net/live-examples/css-examples/text-decoration/text-decoration-color.css"
}
]
}' \
--output "screenshot.png"

Bot detection troubleshooting

If screenshots return blank images, CAPTCHA pages, or content that differs from what a real browser would show, the site is likely blocking automation. Signs include:

  • Blank or white screenshots
  • CAPTCHA challenge pages captured instead of actual content
  • Access denied or 403 error pages in the screenshot
  • Missing or broken page elements compared to a regular browser

The /unblock API is specifically designed to bypass bot detection mechanisms like Datadome and passive CAPTCHAs. It can return a screenshot directly when screenshot: true is set, delivering a base64-encoded PNG of the page after anti-bot measures have been bypassed. For best results, combine it with residential proxies.

Configuration options

The /screenshot API supports shared request configuration options that apply across REST endpoints:

FAQ & Troubleshooting

How do I take a screenshot with the Browserless REST API?

Send a POST request to the /screenshot endpoint with a URL and optional Puppeteer-style screenshot options. The API returns a PNG or JPEG image of the rendered page.

Can I capture a full-page screenshot via the API?

Yes. Set the fullPage option to true in your request body. The API scrolls and captures the entire page content, not just the visible viewport.

What screenshot options are available?

You can set the format (PNG/JPEG), quality, full-page mode, clip region, viewport size, device scale factor, and element-specific selectors. All standard Puppeteer screenshot options are supported.

How do I capture just one element?

Pass a selector at the top level of the request body (alongside url, not inside options). The API waits for the element and crops the capture to its bounding box, so you don't need manual clip math. For a fixed region instead, use options.clip with x, y, width, and height.

Images or content are missing from the capture

Lazy-loaded content only renders when it scrolls into view. Set scrollPage: true at the top level of the request body to scroll through the page before capturing, which triggers lazy loading. Combine it with options.fullPage: true for complete long-page captures.

Next steps

Was this page helpful?