# Website Screenshot Generator — Full Page PNG/JPEG (`keyman98/website-screenshot-generator`) Actor

Capture full-page or viewport screenshots of any list of URLs with real headless Chromium. Desktop or mobile size, PNG or JPEG, cookie-banner removal, pay per screenshot taken.

- **URL**: https://apify.com/keyman98/website-screenshot-generator.md
- **Developed by:** [KeyMan98](https://apify.com/keyman98) (community)
- **Categories:** Developer tools, Automation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.00 / 1,000 screenshot takens

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## Website Screenshot Generator

Capture a screenshot of any list of web pages with a real headless Chromium browser (Playwright). Full page or just the visible viewport, desktop or mobile size, PNG or JPEG — exports the image plus a data row per URL.

### What it does

For each URL in your list, this Actor opens the page in headless Chromium, waits for it to load (and an extra short delay for late content), optionally hides common cookie banners, then takes a screenshot and saves it.

### What you get (output fields)

One dataset row per URL:

- `url` — the URL that was requested.
- `screenshotUrl` — public link to the screenshot image (opens directly in a browser).
- `width` / `height` — actual pixel dimensions of the screenshot.
- `format` — `png` or `jpeg`.
- `fileSizeBytes` — size of the image file.
- `takenAt` — when the screenshot was taken (ISO 8601, UTC).
- `error` — set if the screenshot could not be taken; `null` on success.

The image file itself is saved to the run's key-value store; `screenshotUrl` is the direct public link to it.

### Who it's for

- **Design/QA teams** — visual snapshots of pages across a site or across competitors.
- **No-code/automation builders** — generate a screenshot to embed in a report, email, or dashboard.
- **Monitoring** — periodic visual snapshots of a page (combine with a schedule).

### How to use

1. **URLs** — paste the pages you want screenshotted.
2. **Full page** — off captures only the visible viewport; on captures the entire scrollable page.
3. **Device preset** — Desktop (1280×800), Mobile (390×844), or Custom (set your own width/height).
4. **Format** — PNG (lossless) or JPEG (smaller, adjustable quality).
5. **Delay after load** — extra wait so animations/lazy content settle before the shot.
6. **Wait until** — Load (faster) or Network idle (waits for network activity to quiet down; better for JS-heavy single-page apps, slower).
7. **Hide cookie banners** — best effort; see Limitations.
8. **Run.** Each URL becomes one dataset row plus one image file.

### Input example (JSON)

```json
{
  "urls": [{ "url": "https://example.com" }, { "url": "https://apify.com" }],
  "fullPage": false,
  "devicePreset": "desktop",
  "format": "png",
  "delayMs": 1000,
  "waitUntil": "load",
  "hideCookieBanners": false,
  "timeoutSecs": 30
}
```

### Output example (JSON)

```json
{
  "url": "https://example.com",
  "screenshotUrl": "https://api.apify.com/v2/key-value-stores/.../records/screenshot-abc123.png",
  "width": 1280,
  "height": 800,
  "format": "png",
  "fileSizeBytes": 41230,
  "takenAt": "2026-09-23T10:00:00+00:00",
  "error": null
}
```

### If a page fails to load

That URL is **skipped as an error row**: the rest of the list keeps running, the run does not fail, and you are **not charged** for that URL. The reason (timeout, DNS error, invalid URL, HTTP error) is written to the row's `error` field and to the run log.

### Pricing

Pay only for screenshots actually taken — nothing charged for URLs that failed. Pricing model: **pay-per-event**.

| Event | When it's charged | Price |
| --- | --- | --- |
| `screenshot-taken` | a screenshot was successfully captured and saved | 0.002 USD |

### Limitations

- No login, no CAPTCHA solving, no bypass of any site protection: it screenshots whatever a normal headless browser would see, nothing more.
- "Hide cookie banners" is **best effort**: it hides elements matching a fixed list of common cookie-consent selectors. Many banners use custom markup that is not on that list and will still appear in the screenshot.
- Very long/heavy pages with Full page on can take longer and produce large image files.
- `timeoutSecs` caps how long a single page is given before it is marked as an error row.

### FAQ

#### Can it log in to a site first?

No. It captures whatever the page shows to an anonymous visitor.

#### Can it get past a cookie/consent wall or CAPTCHA?

No, by design.

#### Why is a URL missing an image?

Check its `error` field — the page failed to load or screenshot within the timeout. The run still continues for the other URLs, and you are not charged for the one that failed.

#### Can I set a custom screen size?

Yes, set Device preset to "Custom" and use Viewport width/height.

#### JPEG or PNG — which should I pick?

PNG is lossless and larger; JPEG is smaller with adjustable quality, better for photos/large full-page captures.

#### Can I use this to monitor a page for visual changes?

You can combine it with an Apify schedule to take a screenshot of the same page periodically and build a history of images over time. This Actor does not compare screenshots or detect differences itself — that comparison is up to you.

#### Is it legal to screenshot any website?

Taking a screenshot for personal or internal use (QA, monitoring, a report) is generally fine. Publishing or redistributing screenshots that contain someone else's copyrighted material (logos, photos, branded content) is a separate question this Actor doesn't answer for you. This is not legal advice.

#### Can I use this through the Apify API or an MCP server?

Yes. Like any Apify Actor, you can run it and read results through the standard Apify API, or through the Apify MCP server if you use Claude, Cursor, or another MCP-enabled client.

### Export

Results (URL, screenshot link, dimensions, size) can be downloaded from the Apify dataset as JSON, CSV, or Excel, or accessed via the Apify API. The image files themselves are downloaded from the key-value store, individually via `screenshotUrl` or in bulk via the Apify API.

# Actor input Schema

## `urls` (type: `array`):

Public URLs to screenshot.

## `fullPage` (type: `boolean`):

Capture the entire scrollable page instead of just the visible viewport.

## `devicePreset` (type: `string`):

Pick a screen size preset. Choose "Custom" to set Viewport width/height yourself below.

## `viewportWidth` (type: `integer`):

Browser viewport width in pixels. Only used when Device preset is "Custom".

## `viewportHeight` (type: `integer`):

Browser viewport height in pixels. Only used when Device preset is "Custom".

## `format` (type: `string`):

File format of the screenshot.

## `quality` (type: `integer`):

Compression quality, 1-100. Only used when Image format is JPEG.

## `delayMs` (type: `integer`):

Extra wait time after the page finishes loading, before taking the screenshot (lets late content/animations settle).

## `waitUntil` (type: `string`):

When to consider the page "loaded". "Load" is faster; "Network idle" waits for network activity to quiet down (better for JS-heavy sites, slower).

## `hideCookieBanners` (type: `boolean`):

Try to hide common cookie-consent banners before the screenshot, using a fixed list of common selectors. Best effort only: many banners use custom markup and will not be caught.

## `timeoutSecs` (type: `integer`):

Maximum time to spend loading and screenshotting a single page before giving up on it as an error.

## Actor input object example

```json
{
  "urls": [
    {
      "url": "https://example.com"
    },
    {
      "url": "https://apify.com"
    }
  ],
  "fullPage": false,
  "devicePreset": "desktop",
  "viewportWidth": 1280,
  "viewportHeight": 800,
  "format": "png",
  "quality": 80,
  "delayMs": 1000,
  "waitUntil": "load",
  "hideCookieBanners": false,
  "timeoutSecs": 30
}
```

# Actor output Schema

## `results` (type: `string`):

All results in the default dataset (JSON, CSV, Excel).

## `screenshots` (type: `string`):

Screenshot images stored in the key-value store.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "urls": [
        {
            "url": "https://example.com"
        },
        {
            "url": "https://apify.com"
        }
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("keyman98/website-screenshot-generator").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = { "urls": [
        { "url": "https://example.com" },
        { "url": "https://apify.com" },
    ] }

# Run the Actor and wait for it to finish
run = client.actor("keyman98/website-screenshot-generator").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "urls": [
    {
      "url": "https://example.com"
    },
    {
      "url": "https://apify.com"
    }
  ]
}' |
apify call keyman98/website-screenshot-generator --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,keyman98/website-screenshot-generator"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/JTOFfdCP5EpbvFZkd/builds/obEQwjIqN1gZdAMfy/openapi.json
