Website Screenshot API, Full Page & URL/HTML to PDF avatar

Website Screenshot API, Full Page & URL/HTML to PDF

Pricing

from $2.00 / 1,000 files

Go to Apify Store
Website Screenshot API, Full Page & URL/HTML to PDF

Website Screenshot API, Full Page & URL/HTML to PDF

Website screenshot API and URL/HTML to PDF converter. Full-page PNG, JPEG, WebP and A4/Letter PDF from one page load. Batch from a URL list, sitemap or dataset; iPhone/Android views; cookie banners hidden; visual regression diff. $2 per 1,000 files, failed URLs free.

Pricing

from $2.00 / 1,000 files

Rating

0.0

(0)

Developer

Rigel

Rigel

Maintained by Community

Actor stats

0

Bookmarked

2

Total users

1

Monthly active users

17 hours ago

Last modified

Share

Take a website screenshot (viewport, full page, one element, or a mobile view) and convert URLs or raw HTML to PDF, in bulk, from one Apify Actor. Each page is loaded once in headless Chromium, then every format you ask for (PNG, JPEG, WebP, PDF) comes from that same load. You pay $0.002 per stored file. Failed, blocked and skipped URLs are free.

  • Full-page screenshots up to 16,384 px tall, with lazy images scrolled into view.
  • Mobile and tablet views: iPhone 15, Pixel 8, iPad, plus desktop, laptop, MacBook Retina and a 1200×630 Open Graph card.
  • URL to PDF and HTML to PDF: A4, Letter, Legal or A3, margins, landscape, backgrounds, page numbers, custom header and footer.
  • Batch input: a list of URLs, a sitemap.xml (indexes and .xml.gz followed), or the URLs of an existing dataset. Up to 5,000 URLs per run.
  • Visual regression diff: compare each screenshot with the previous run and get percentChanged plus a diff image.
  • Clean captures: common cookie banners hidden with CSS, ads and trackers blocked, dark mode, custom CSS, hide or blur selectors.
  • API-first: REST, Python, JavaScript, sync endpoint that returns the file bytes, MCP for AI agents, n8n and Make.

Social networks and private network addresses are refused before any navigation (see Legal and safety).

Use cases

You want to…Use these inputs
Archive how a page looked, as an image and a PDFformats: ["png", "pdf"], fullPage: true
Check a responsive layout on a phonedevice: "iphone_15" or "pixel_8"
Turn a list of documentation or report pages into PDFsurls: [...], formats: ["pdf"], pdf.format: "A4"
Generate PDF invoices, receipts or reports from your own HTMLhtml: "<html>…", formats: ["pdf"]
Get alerted when a page changes visually (visual regression testing)compareWithPrevious: true + an Apify schedule
Make thumbnails of every page of your sitesitemapUrl, formats: ["jpeg"], quality: 75
Capture a single chart, pricing table or widgetselector: ".pricing-table"
Create link-preview / Open Graph imagesdevice: "og_card" (1200×630)

Ready-made examples: Full-page PNG · iPhone view · Bulk URL to A4 PDF · HTML invoice to PDF · Visual regression diff · Element screenshot · Sitemap thumbnails · Open Graph image

Pricing

Pay per event. Compute is included: there is no separate charge for CPU or memory.

EventPriceWhen
Actor start$0.0005 per GB of run memoryOnce per run. At the default 2 GB this is $0.001; at the 1 GB minimum, $0.0005.
File$0.002One PNG, JPEG, WebP or PDF stored. PNG + PDF of the same page = 2 files.
Visual diff$0.001Only when a baseline already existed and a diff was computed. The first run, which creates the baseline, is not charged for a diff.

Not charged: invalid URLs, blocked domains, private addresses, DNS or connection errors, HTTP 4xx/5xx (unless you turn on captureErrorPages), timeouts, missing selectors, non-HTML responses (PDF or ZIP downloads), duplicates, and URLs skipped after your spending limit is reached.

What a run costs (default 2 GB memory)

RunFilesCost
1 URL, one PNG1$0.003
1 URL, PNG + PDF2$0.005
One raw HTML invoice to PDF1$0.003
100 URLs, full-page PNG100$0.201
1,000 URLs to PDF1,000$2.001
1,000 URLs, PNG + PDF2,000$4.001
50 URLs checked daily with visual diff (after the first run)50 + 50 diffs$0.151 per run, about $4.53 per month

Set a maximum cost per run in Apify Console or with maxTotalChargeUsd in the API: when it is reached, the remaining URLs are returned as skipped and not charged.

Input examples

All field names below are the real input fields of this Actor. Only one source is required: urls, html, sitemapUrl or datasetId.

Full-page screenshot, desktop

{
"urls": [{ "url": "https://en.wikipedia.org/wiki/Screenshot" }],
"formats": ["png"],
"fullPage": true,
"device": "desktop"
}

Mobile screenshot (iPhone 15, 393×852 at 3×)

{
"urls": [{ "url": "https://www.wikipedia.org/" }],
"formats": ["png"],
"device": "iphone_15"
}

Bulk URL to PDF, A4 with page numbers

{
"urls": [
{ "url": "https://example.com/" },
{ "url": "https://en.wikipedia.org/wiki/PDF" },
{ "url": "https://docs.apify.com/platform/actors" }
],
"formats": ["pdf"],
"pdf": {
"format": "A4",
"landscape": false,
"printBackground": true,
"pageNumbers": true,
"margin": { "top": "1cm", "right": "1cm", "bottom": "1.4cm", "left": "1cm" }
}
}

HTML to PDF (your own HTML, up to 2 MB)

{
"html": "<!doctype html><html><body><h1>Invoice INV-001</h1><p>Total: $2.50</p></body></html>",
"formats": ["pdf"],
"pdf": { "format": "Letter", "pageNumbers": true }
}

Visual regression: diff against the previous run

{
"urls": [{ "url": "https://example.com/" }],
"formats": ["png"],
"compareWithPrevious": true,
"baselineStoreName": "rigel-screenshot-baselines",
"diffThreshold": 0.1
}

Screenshots of a whole site from its sitemap

{
"sitemapUrl": "https://docs.apify.com/sitemap.xml",
"maxUrls": 50,
"formats": ["jpeg"],
"quality": 75,
"device": "laptop"
}

One element only, at 2× density

{
"urls": [{ "url": "https://en.wikipedia.org/wiki/Portable_Network_Graphics" }],
"formats": ["png"],
"selector": ".infobox",
"deviceScaleFactor": 2
}

Other useful fields: width / height / deviceScaleFactor to override a device, clip ({x, y, width, height}), omitBackground (transparent PNG/WebP), waitUntil (load, domcontentloaded, networkidle), waitForSelector, delayMs, scrollToLoad, timeoutSecs (per page, 5–90 s), darkMode, hideCookieBanners, acceptCookies, blockAds, hideSelectors, blurSelectors, customCss, maxConcurrency (1–8), datasetId + urlField.

Output

Files go to the run's default key-value store. Key format: <host>-<10-char hash of URL and options>.<ext> (raw HTML: html-<hash>.<ext>). OUTPUT holds a copy of the first stored file and RUN_SUMMARY.json has counts, events and duration.

The dataset has one row per URL:

{
"url": "https://example.com/",
"finalUrl": "https://example.com/",
"status": "ok",
"errorCode": null,
"httpStatus": 200,
"files": [
{
"format": "png",
"key": "example.com-0b5df33ae2.png",
"url": "https://api.apify.com/v2/key-value-stores/STORE_ID/records/example.com-0b5df33ae2.png?signature=…",
"bytes": 78288,
"width": 1920,
"height": 1080,
"truncated": false
}
],
"page": { "title": "Example Domain", "lang": "en", "loadMs": 119, "consoleErrors": 0 },
"visualDiff": { "baselineFound": true, "percentChanged": 0, "changedPixels": 0, "diffKey": "diff-example.com-0b5df33ae2.png" },
"charged": { "capture": 1, "visual-diff": 1 }
}

files[].url is a signed link that opens without your API token. PDFs have pages instead of width/height. status is ok, failed, blocked or skipped, with a stable errorCode (for example NAVIGATION_TIMEOUT, HTTP_ERROR, SELECTOR_NOT_FOUND, BLOCKED_DOMAIN). visualDiff is null unless compareWithPrevious is on. The dataset has two views: Overview and Errors.

Use it from the API

Get your token in Apify Console › Settings › API & Integrations.

cURL: get the file bytes in one call (sync endpoint, returns the OUTPUT record)

curl -X POST "https://api.apify.com/v2/acts/rigel~website-screenshot-pdf/run-sync-get-output" \
-H "Authorization: Bearer $APIFY_TOKEN" \
-H "Content-Type: application/json" \
-d '{"urls":[{"url":"https://example.com"}],"formats":["pdf"],"pdf":{"format":"A4","pageNumbers":true}}' \
--output page.pdf

Python (pip install "apify-client>=3")

import os
import requests
from apify_client import ApifyClient
client = ApifyClient(os.environ["APIFY_TOKEN"])
run = client.actor("rigel/website-screenshot-pdf").call(run_input={
"urls": [{"url": "https://example.com"}, {"url": "https://en.wikipedia.org/wiki/PDF"}],
"formats": ["png", "pdf"],
"fullPage": True,
})
for row in client.dataset(run.default_dataset_id).iterate_items():
for f in row.get("files", []):
with open(f["key"], "wb") as out:
out.write(requests.get(f["url"], timeout=60).content)
print(row["status"], f["key"], f["bytes"])

JavaScript / Node.js (npm install apify-client)

import { ApifyClient } from 'apify-client';
import { writeFile } from 'node:fs/promises';
const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const run = await client.actor('rigel/website-screenshot-pdf').call({
urls: [{ url: 'https://example.com' }],
formats: ['png'],
device: 'iphone_15',
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
for (const row of items) {
for (const f of row.files ?? []) {
const res = await fetch(f.url);
await writeFile(f.key, Buffer.from(await res.arrayBuffer()));
console.log(row.status, f.key, f.bytes);
}
}

Use it from AI agents (MCP)

Add the Apify MCP server with only this Actor as a tool:

{ "mcpServers": { "website-screenshot": { "url": "https://mcp.apify.com?tools=rigel/website-screenshot-pdf" } } }

or claude mcp add --transport http website-screenshot "https://mcp.apify.com?tools=rigel/website-screenshot-pdf". Sign in with OAuth or send Authorization: Bearer <APIFY_TOKEN>. The agent passes the same input as above and reads files[].url from the result.

n8n and Make

  • n8n: Apify node › Run an Actor (rigel/website-screenshot-pdf, wait for finish) › Apify node › Get dataset items › HTTP Request on files[0].url to download the PNG or PDF. For visual regression, add an IF node on visualDiff.percentChanged > 1 and send yourself an email or a Slack message.
  • Make: Apify app › Run an Actor (synchronous) › Get Dataset Items › HTTP › Get a file on files[].url.
  • Schedules: an Apify schedule on a saved task with compareWithPrevious: true gives you a daily visual check without n8n or Make.

Keep cookies, headers and proxyUrl out of logged steps: they are secret inputs.

  • PDF to Markdown for RAG & LLMs: when a URL is a PDF, DOCX or other file (NOT_A_WEB_PAGE, not charged here), send it there to get Markdown or RAG chunks with page numbers.

FAQ

Do I pay for URLs that fail? No. Only stored files and computed diffs are charged, plus the start event of the run.

Can I take a full-page screenshot of a very long page? Yes, up to 16,384 device pixels tall. Longer pages are cut and the file is flagged truncated: true. Lazy images are scrolled into view first for full-page captures.

How do I convert HTML to PDF without hosting it? Put the HTML string in html and set formats: ["pdf"]. CSS, web fonts and images referenced by public URLs are rendered. One HTML document per run.

How does the visual diff work? With compareWithPrevious: true, the PNG of each URL is compared pixel by pixel (pixelmatch) with the baseline stored by the previous run in the named key-value store baselineStoreName of your account, then the baseline is replaced. The diff image key is in visualDiff.diffKey. Changing the device or capture options creates a new baseline.

Can it capture pages behind a login? You can pass cookies and headers for your own site. They are sent only to the target origin, never to third parties or after a redirect to another origin, and never logged. You must have the right to access and capture the page.

Can I use a proxy? Yes, your own http or socks5 proxy in proxyUrl. Apify Proxy is not used.

How fast is it? Pages run in parallel: 2 at the default 2 GB, 3 at 4 GB, or set maxConcurrency (1–8). A simple page takes about 1 second of browser time.

How long are the files kept? They live in the run's key-value store, which follows the data retention of your Apify plan. Download them or copy them to your own storage if you need them longer.

Why was my URL refused? Social and profile platforms (Facebook, Instagram, LinkedIn, TikTok, X, Reddit and others) are blocked, as well as private and loopback addresses. File downloads such as PDF links return NOT_A_WEB_PAGE, free of charge. To convert documents to text, use rigel/doc-to-markdown.

Zapier: my Zap times out. Zapier's synchronous "Run Actor" action stops waiting after 30 seconds. For batches, run the Actor asynchronously and start the next step from Apify's "Finished Actor run" trigger, then read the results with the "Fetch dataset items" search.

Limits

  • 5,000 URLs per run (maxUrls), 2 MB of raw HTML, 8 KB of custom CSS.
  • Per-page timeout 5–90 seconds (default 30).
  • Full-page height capped at 16,384 device pixels.
  • A browser crash is retried once, then returned as BROWSER_CRASH, free of charge.

You need the right to capture each page; the Actor does not decide that for you. It does not collect accounts, profiles or personal data, and it does not log page content, cookies or request headers. Social and profile platforms are blocked in code. Loopback, private (RFC 1918), link-local (including cloud metadata), CGNAT and IPv6 unique-local addresses are rejected for the page, its redirects and its subresources.

Support

Open an issue on the Issues tab. Bug reports with the run ID get the fastest answer.