Screenshot — Getting Started

Prerequisites: Make sure you have created an account and API key first.

Introduction

Nodium Screenshot API is a high-performance web capture service that converts any URL, raw HTML, or Markdown into pixel-perfect screenshots, PDFs, and videos via a simple REST API.

What you can do:

  • Capture any public or authenticated web page as PNG, JPEG, WebP, AVIF, or other image formats
  • Render raw HTML or Markdown content into images
  • Generate PDFs with full control over paper size, margins, and orientation
  • Record animated scroll videos as MP4, WebM, or GIF
  • Extract page metadata (Open Graph, fonts, favicon, HTTP headers)
  • Analyze screenshots with OpenAI Vision

Base URL:

https://api.nodium.io/api/v1/screenshot

Authentication

Every request requires an API key. Obtain your key from the Nodium Dashboard under API Keys. Enable the screenshot scope when creating or editing the key.

There are three ways to provide your API key:

1. Query parameter

?access_key=YOUR_API_KEY

2. HTTP header

X-Access-Key: YOUR_API_KEY

3. JSON body (POST only)

json
{
  "access_key": "YOUR_API_KEY",
  "url": "https://example.com"
}
Security recommendation: Use the HTTP header method for production applications. Avoid placing your API key in query strings that may appear in server logs or browser history. For public-facing integrations, use signed URLs.

Your First Screenshot

Capture a screenshot of example.com in one line:

bash
curl "https://api.nodium.io/api/v1/screenshot/take?access_key=YOUR_API_KEY&url=https://example.com&format=png" \
  -o screenshot.png

The API returns the raw image bytes. Open screenshot.png to see the result.


Code Examples

cURL

bash
# Basic screenshot
curl "https://api.nodium.io/api/v1/screenshot/take?access_key=YOUR_API_KEY&url=https://example.com&format=png" \
  -o screenshot.png

# Full-page screenshot with custom viewport
curl -X POST "https://api.nodium.io/api/v1/screenshot/take" \
  -H "Content-Type: application/json" \
  -H "X-Access-Key: YOUR_API_KEY" \
  -d '{
    "url": "https://example.com",
    "format": "jpeg",
    "full_page": true,
    "viewport_width": 1440,
    "viewport_height": 900,
    "image_quality": 90
  }' \
  -o fullpage.jpg

# Mobile device emulation
curl "https://api.nodium.io/api/v1/screenshot/take?access_key=YOUR_API_KEY&url=https://example.com&format=webp&viewport_device=iphone_16_pro" \
  -o mobile.webp

Node.js (fetch)

javascript
const fs = require("fs");

async function takeScreenshot() {
  const response = await fetch(
    "https://api.nodium.io/api/v1/screenshot/take",
    {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        "X-Access-Key": "YOUR_API_KEY",
      },
      body: JSON.stringify({
        url: "https://example.com",
        format: "png",
        viewport_width: 1280,
        viewport_height: 1024,
      }),
    }
  );

  if (!response.ok) {
    const error = await response.json();
    throw new Error(`${error.error_code}: ${error.message}`);
  }

  const buffer = Buffer.from(await response.arrayBuffer());
  fs.writeFileSync("screenshot.png", buffer);
  console.log("Screenshot saved!");
}

takeScreenshot();

Python (requests)

python
import requests

response = requests.get(
    "https://api.nodium.io/api/v1/screenshot/take",
    params={
        "access_key": "YOUR_API_KEY",
        "url": "https://example.com",
        "format": "png",
        "viewport_width": 1280,
        "viewport_height": 1024,
    },
)

if response.status_code == 200:
    with open("screenshot.png", "wb") as f:
        f.write(response.content)
    print("Screenshot saved!")
else:
    error = response.json()
    print(f"Error: {error['error_code']} - {error['message']}")

PHP (curl)

php
<?php

$params = http_build_query([
    'access_key'     => 'YOUR_API_KEY',
    'url'            => 'https://example.com',
    'format'         => 'png',
    'viewport_width' => 1280,
    'viewport_height'=> 1024,
]);

$ch = curl_init("https://api.nodium.io/api/v1/screenshot/take?{$params}");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);

$response = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($httpCode === 200) {
    file_put_contents('screenshot.png', $response);
    echo "Screenshot saved!\n";
} else {
    $error = json_decode($response, true);
    echo "Error: {$error['error_code']} - {$error['message']}\n";
}

Output Formats

Image Formats

Formatformat=TransparencyCompressionBest For
PNGpngYesLosslessUI screenshots, pixel-perfect captures
JPEGjpegNoLossyPhotos, general-purpose, smaller files
WebPwebpYesBothWeb delivery, best size/quality ratio
AVIFavifYesLossyMaximum compression, modern browsers
HEIFheifYesLossyApple ecosystem
TIFFtiffYesLosslessPrint, archival
JP2jp2YesBothHigh-quality archival
GIFgifYesLosslessSimple graphics (static; use /animate for animated)

Document Formats

Formatformat=Best For
PDFpdfReports, invoices, printable documents
HTMLhtmlExtracting rendered HTML source
MarkdownmarkdownContent extraction in Markdown format

Video Formats (endpoint /animate only)

Formatformat=Best For
MP4mp4Universal video playback
WebMwebmWeb-optimized video
GIFgifSocial media, email embeds
MOVmovApple ecosystem, transparent background support
AVIaviLegacy systems

Response Types

Control what the API returns with the response_type parameter:

ValueContent-TypeDescription
by_format (default)Matches format (e.g. image/png)Returns the raw binary file (image, PDF, or video)
jsonapplication/jsonReturns JSON with screenshot URL, metadata, and cache info
emptynoneReturns only HTTP status and headers (fastest)

JSON response example

json
{
  "screenshot_url": "https://cdn.nodium.io/screenshots/abc123.png",
  "cache_url": "https://cdn.nodium.io/cache/abc123.png",
  "metadata": {
    "image_size": { "width": 1280, "height": 1024 },
    "page_title": "Example Domain"
  }
}

Response headers

Every response includes informational headers:

HeaderDescription
x-nodium-rendering-secondsTime spent rendering (e.g. 2.34)
x-nodium-size-bytesOutput file size in bytes
x-nodium-referenceUnique screenshot reference ID
x-nodium-trace-idTrace ID for debugging
x-nodium-cache-urlURL to the cached screenshot (if caching enabled)

Error Handling

Error response format

When an error occurs, the API returns a JSON body regardless of response_type:

json
{
  "error_code": "request_not_valid",
  "message": "The request parameters are not valid. Check the request body or query string.",
  "http_status_code": 400
}

Common error codes

Error CodeHTTP StatusCause
access_key_required400Missing API key
access_key_invalid400Invalid or revoked API key
request_not_valid400Invalid parameters
screenshots_limit_reached400Monthly quota exceeded
concurrency_limit_reached400Too many simultaneous requests
timeout_error500Page took too long to load
network_error500Cannot reach the target URL
internal_application_error500Server error (safe to retry)
temporary_unavailable503Service overloaded (safe to retry)

Retry strategy

For production applications, implement exponential backoff on retryable errors:

  • Retry on: 500 (internal_application_error, network_error, timeout_error) and 503 (temporary_unavailable)
  • Do not retry on: 400 errors (fix the request first)
  • Recommended: 3 retries with delays of 1s, 2s, 4s
javascript
async function takeScreenshotWithRetry(params, maxRetries = 3) {
  for (let attempt = 0; attempt <= maxRetries; attempt++) {
    const response = await fetch(
      "https://api.nodium.io/api/v1/screenshot/take",
      {
        method: "POST",
        headers: {
          "Content-Type": "application/json",
          "X-Access-Key": "YOUR_API_KEY",
        },
        body: JSON.stringify(params),
      }
    );

    if (response.ok) return response;

    const error = await response.json();

    // Do not retry client errors
    if (response.status < 500) throw new Error(error.message);

    // Exponential backoff
    if (attempt < maxRetries) {
      await new Promise((r) => setTimeout(r, 1000 * Math.pow(2, attempt)));
    }
  }
  throw new Error("Max retries exceeded");
}

Next Steps

Now that you know the basics, explore the rest of the documentation:

  • API Reference -- Complete reference for all 145+ parameters, endpoints, error codes, and response headers
  • Guides -- Practical guides for common use cases: full-page captures, PDF generation, authenticated pages, animated screenshots, webhooks, and more