ScreenshotNeo

BlogHow-to

How to Take Scheduled Website Screenshots with Browserless

Schedule recurring Browserless captures with Zapier or your own scheduler, save the image response, and choose settings that capture the right page content.

By the ScreenshotNeo team4 October 20269 min read

To take scheduled website screenshots with Browserless, use a scheduler to trigger an HTTP POST to Browserless’s /screenshot endpoint. Include your API token, the page URL, and screenshot options in the request; save the binary image response or pass it to a later delivery step. Browserless documents this workflow with Schedule by Zapier and Webhooks by Zapier. Its hourly schedule is an example cadence, not a recommendation for every site. Browserless Screenshot API documentation · Browserless Zapier guide

1. Choose a schedule and get an API token

A scheduled capture has two parts: a recurring trigger and a screenshot request. The scheduler might be a visual automation tool such as Zapier, or a cron job that runs your own script. Browserless performs the browser capture when the request arrives; the scheduler determines when that happens.

  1. Create or select a Browserless account and get an API token from its dashboard. Treat the token as a secret. Store it in your scheduler’s credential field or an environment variable rather than in published code.
  2. Choose a cadence that matches the monitoring need. For example, a page that changes several times a day may need more frequent snapshots than a weekly archive. Consider the scheduler’s limits and your Browserless account’s current usage terms; this guide does not assume a particular quota or price.
  3. Decide what the image is for: viewport monitoring, a full-page archive, a thumbnail, or a particular page region. That choice determines capture settings and where you send the result.

2. Schedule captures with Zapier

Browserless’s documented Zapier example uses Schedule by Zapier as the trigger, Webhooks by Zapier to POST to the screenshot endpoint, and optionally Gmail to attach the returned image. The example uses an hourly trigger and a 1440 × 1000 viewport. Set your own interval and target page for the job.

  1. Create a Zap with Schedule by Zapier as the trigger. Select the cadence that suits the monitoring task.
  2. Add Webhooks by Zapier and choose the POST event.
  3. Set the request URL to your Browserless regional screenshot endpoint with your token as a query parameter. The current REST API documentation uses this form: https://production-sfo.browserless.io/screenshot?token=YOUR_API_TOKEN. Use the endpoint and region shown for your account.
  4. Set the payload type to JSON and provide a body like the one below. Put your actual target URL in url; adjust the viewport and full-page setting as needed.
  5. Run a test capture and inspect the image. Confirm that the automation platform exposes the response as a file or binary value before configuring an attachment or storage step.
  6. Optionally add a downstream action, such as sending the image as an email attachment or storing it in a destination supported by your automation.
{
  "url": "https://example.com/",
  "options": {
    "fullPage": true,
    "type": "png",
    "viewport": { "width": 1440, "height": 1000 }
  }
}

The API response is image data, not a JSON object containing an image URL. A successful response uses an image content type such as image/png; configure the next step to consume the returned file rather than treating it as ordinary text.

3. Run a scheduled capture with code

If you already have a scheduler, run a script on its schedule and save each response to a timestamped path. The examples below use the documented Browserless REST API shape and write the returned bytes to disk. Replace the placeholder token, target URL, and output path. Keep the token in a secret store or environment variable in production.

cURL

curl --fail-with-body -sS -X POST \
  "https://production-sfo.browserless.io/screenshot?token=YOUR_API_TOKEN" \
  -H "Cache-Control: no-cache" \
  -H "Content-Type: application/json" \
  -d '{
    "url": "https://example.com/",
    "options": {
      "fullPage": true,
      "type": "png",
      "viewport": { "width": 1440, "height": 1000 }
    }
  }' \
  --output screenshot.png

--fail-with-body makes HTTP errors visible as command failures while retaining any response body for diagnosis. If your installed cURL predates support for that option, remove it and check the HTTP status separately.

Python

import os
from pathlib import Path
from datetime import datetime, timezone

import requests

TOKEN = os.environ["BROWSERLESS_TOKEN"]
endpoint = "https://production-sfo.browserless.io/screenshot"
payload = {
    "url": "https://example.com/",
    "options": {
        "fullPage": True,
        "type": "png",
        "viewport": {"width": 1440, "height": 1000},
    },
}

response = requests.post(
    endpoint,
    params={"token": TOKEN},
    headers={"Cache-Control": "no-cache"},
    json=payload,
    timeout=90,
)
response.raise_for_status()

stamp = datetime.now(timezone.utc).strftime("%Y%m%dT%H%M%SZ")
Path(f"screenshot-{stamp}.png").write_bytes(response.content)

Install the dependency with python -m pip install requests. Set BROWSERLESS_TOKEN in the job’s environment or secret manager before running the script.

Node.js

import { writeFile } from "node:fs/promises";

const token = process.env.BROWSERLESS_TOKEN;
if (!token) throw new Error("Set BROWSERLESS_TOKEN");

const endpoint = new URL("https://production-sfo.browserless.io/screenshot");
endpoint.searchParams.set("token", token);

const response = await fetch(endpoint, {
  method: "POST",
  headers: {
    "Cache-Control": "no-cache",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    url: "https://example.com/",
    options: {
      fullPage: true,
      type: "png",
      viewport: { width: 1440, height: 1000 },
    },
  }),
  signal: AbortSignal.timeout(90_000),
});

if (!response.ok) {
  const detail = await response.text();
  throw new Error(`Browserless HTTP ${response.status}: ${detail}`);
}

const image = Buffer.from(await response.arrayBuffer());
await writeFile("screenshot.png", image);

Run with a Node.js version that supports built-in fetch and AbortSignal.timeout, or use an HTTP client and timeout mechanism available in your runtime.

4. Pick settings for a useful scheduled image

The request body accepts the page URL and screenshot options. Browserless documents PNG, JPEG, and WebP output, viewport and full-page capture, clipping, selectors, waiting controls, navigation options, and request blocking. Check its current API reference for the precise schema and defaults for your endpoint.

Need Setting or approach Notes
Capture the whole document options.fullPage: true Useful for archives and visual review of long pages. Very tall pages can produce large images and longer jobs.
Keep layout consistent options.viewport Set width and height explicitly so responsive breakpoints do not change between runs.
Choose file format options.type: png, jpeg, or webp PNG is useful for crisp text and visual comparison. JPEG is lossy; its quality option applies when using JPEG. WebP can be useful when the consumer supports it.
Capture lazy-loaded content Top-level scrollPage: true, with full-page capture if needed Scrolling can trigger content that only loads when it enters view. Inspect the result, since page behavior varies.
Wait for a page state Wait controls, selector waits, timeout or gotoOptions Use a specific selector or wait condition when the content is rendered asynchronously. Avoid assuming navigation completion means every widget or data request has finished.
Capture one element Top-level selector The API can capture an element by selector. Use a stable selector and ensure the element exists before capture.
Capture a fixed region options.clip with coordinates and dimensions Coordinates depend on the page layout and viewport; validate the crop at the chosen viewport.
Reduce unwanted loading rejectResourceTypes or rejectRequestPattern Blocking resources may speed up a job, but blocking scripts, fonts, or styles can change the rendered page.
Continue after some wait failures bestAttempt Use only when a partial capture is acceptable; otherwise surface the failed wait and investigate.

Browserless also documents adding CSS or scripts before capture and launch parameters for configuring the browser. These are useful when you need a controlled presentation, but injected code changes what the screenshot represents. Keep the request reproducible and document any transformations in the monitoring job. Screenshot API options · Launch parameters

5. Schedule it reliably

  • Name captures by time. Use an unambiguous UTC timestamp in the filename or storage key so repeated runs do not overwrite each other.
  • Check both transport and content. An HTTP success and a valid image can still contain a CAPTCHA, a blank page, an error screen, or incomplete content. Review the output at setup and sample it periodically.
  • Set timeouts deliberately. Use an HTTP client timeout long enough for navigation and rendering, but bounded so a hung capture does not stall the scheduler indefinitely. Browserless documents a 30-second default timeout for its BrowserQL screenshot operation; do not assume that default applies to every API surface.
  • Handle failed runs. Record the scheduled time, target, HTTP status, and error details. Configure the scheduler to retry transient failures only where duplicate delivery or storage is safe.
  • Avoid overlapping jobs. If a capture can take longer than the interval, decide whether to skip, queue, or allow overlapping runs. The right behavior depends on whether every snapshot is needed.
  • Protect credentials and images. Do not publish token-bearing endpoint URLs in logs or shared dashboards. Apply access controls and retention settings in the storage and delivery systems you choose.

6. Troubleshooting

Symptom Likely cause What to check
Unauthorized or token error Missing, invalid, or incorrectly encoded token Confirm the token is present in the query string and belongs to the account. Check that the scheduler did not remove or alter query parameters.
JSON or text saved with a PNG filename The server returned an error body and the client saved it as an image Check HTTP status and response content type before writing the file. Use raise_for_status() or equivalent error handling.
Blank or white screenshot The page did not render as expected, is blocked, or the capture happened too early Inspect the page in a regular browser, add an appropriate wait, and check for bot checks or access-denied content. Browserless documents its /unblock API for anti-bot cases; it does not guarantee access to every site. Browserless troubleshooting guidance
CAPTCHA or access denied in the image The site is blocking automated browser traffic Confirm the site permits the capture. Browserless points to /unblock for some anti-bot cases, but a successful result is not guaranteed.
Images or page sections are missing Lazy content has not loaded, rendering is asynchronous, or resources were blocked Try scrollPage: true, wait for a meaningful selector, review blocked resource settings, and compare a fresh output.
Zapier step succeeds but the next step cannot attach the image The response is binary data and the automation step may expose it differently than expected Inspect the webhook test output and configure the next action to use the file/binary response field. Test the complete path with one run.
Capture takes too long or times out Slow navigation, long-running page requests, a large full-page image, or an overly strict wait Use a narrower capture, a reasonable wait condition, and bounded client timeout. Check whether a fixed viewport capture is sufficient.
Layout changes between runs Viewport, responsive breakpoint, fonts, or page content differs Set viewport dimensions consistently and account for dynamic page data, animations, and time-dependent content.

7. Performance and cost considerations

Each scheduled run makes a browser capture request, so request volume grows with both the number of pages and the frequency. Estimate the monthly run count as pages × runs per day × days, then account for retries and manual captures. The reviewed Browserless documentation describes the endpoint and workflow but does not establish current plan prices or quotas; check your account’s current terms before choosing a cadence.

Full-page captures, large viewports, slow pages, and waits for network activity can increase response time and image size. Capture only the region or format your downstream use needs, and block unnecessary resources only after confirming the rendered page remains accurate. A screenshot response contains the image bytes, so large images also affect transfer, storage, and delivery costs in your own systems.

Or skip the browser setup

ScreenshotNeo is a website screenshot API and MCP server. One GET request returns a PNG, JPEG, WebP, or PDF. Its pre-capture cleanup accepts cookie and consent banners and removes more than 60 known consent platforms, newsletter popups, and chat widgets; each step can be turned off. Bot checks and CAPTCHAs, blank pages, timeouts, failed loads, and cache hits cost nothing, and responses identify the page verdict and billing status in headers. An MCP server provides take_screenshot, get_page_info, and capture_pdf tools for AI agents.

For full options and configuration, 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
import requests
r = requests.get("https://api.screenshotneo.com/v1/shot", params={"access_key": "YOUR_API_KEY", "url": "https://example.com"}, timeout=90)
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://example.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);

ScreenshotNeo includes 1,000 screenshots per month free with no card; paid plans start at $5 for 3,000. Sign up for free and get 1,000 screenshots a month with no card.

FAQ

Can Browserless take screenshots automatically every hour?

Yes. Browserless’s Zapier guide shows an hourly Schedule by Zapier trigger followed by a webhook POST. Choose that interval only if it fits your monitoring purpose.

Does the scheduler run the browser?

The scheduler initiates the request. Browserless handles the browser capture and returns the image response.

Does a successful request prove the page was captured correctly?

No. Inspect the image for the expected page and content; a valid response can still show a block page, blank content, or an incomplete render.

When should I use a browser automation script instead of the REST endpoint?

The REST endpoint is suited to a single capture request. If the workflow needs substantial interaction before capture, Browserless also documents using Puppeteer or Playwright connections.