DEV Community

Jonathan Geiger
Jonathan Geiger

Posted on • Originally published at capturekit.dev

How to Take Screenshots with Puppeteer

Capturing website screenshots programmatically is a crucial task for developers, testers, and automation engineers. Puppeteer, a Node.js library, provides a powerful way to interact with web pages via the Chrome DevTools Protocol. In this guide, we'll explore how to take high-quality screenshots with Puppeteer and handle common challenges.

What is Puppeteer?

Puppeteer is a high-level API for controlling headless Chrome or Chromium. It allows developers to:

  • Automate UI testing
  • Capture screenshots and PDFs
  • Scrape data from web pages
  • Perform performance monitoring
  • Simulate user interactions (clicks, typing, form submissions)

Let's dive into using Puppeteer for screenshot automation.

Installing Puppeteer

First, install Puppeteer via npm:

npm install puppeteer
Enter fullscreen mode Exit fullscreen mode

This will download a compatible Chromium version along with Puppeteer. If you prefer using an existing Chrome installation, use puppeteer-core instead:

npm install puppeteer-core
Enter fullscreen mode Exit fullscreen mode

Taking a Simple Screenshot

Here's a basic script to capture a screenshot of example.com:

const puppeteer = require('puppeteer');

(async () => {
    const browser = await puppeteer.launch();
    const page = await browser.newPage();
    await page.goto('https://example.com');
    await page.screenshot({ path: 'example.png' });
    await browser.close();
})();
Enter fullscreen mode Exit fullscreen mode

This script:

  1. Launches a headless browser
  2. Opens a new page
  3. Navigates to https://example.com
  4. Captures a screenshot and saves it as example.png
  5. Closes the browser

Capturing Full-Page Screenshots

For full-page screenshots, use the fullPage option:

await page.screenshot({ path: 'fullpage.png', fullPage: true });
Enter fullscreen mode Exit fullscreen mode

This ensures the entire scrollable page is captured.

Handling High-Resolution Screenshots

To capture pixel-perfect screenshots on Retina displays, set the viewport scale:

await page.setViewport({
    width: 1920,
    height: 1080,
    deviceScaleFactor: 2,
});
Enter fullscreen mode Exit fullscreen mode

Waiting for Elements to Load

Use waitUntil: "networkidle2" to wait until all requests are complete:

await page.goto('https://example.com', { waitUntil: 'networkidle2' });
Enter fullscreen mode Exit fullscreen mode

For dynamic content, wait for a specific element:

await page.waitForSelector('#important-element', { visible: true });
Enter fullscreen mode Exit fullscreen mode

Capturing a Specific Page Section

To capture a portion of the page, use the clip option:

await page.screenshot({
    path: 'section.png',
    clip: { x: 100, y: 100, width: 600, height: 400 },
});
Enter fullscreen mode Exit fullscreen mode

Capturing an Element Screenshot

const element = await page.$('#target-element');
await element.screenshot({ path: 'element.png' });
Enter fullscreen mode Exit fullscreen mode

Blocking Ads and Trackers

To speed up screenshots, block unnecessary network requests:

await page.setRequestInterception(true);
page.on('request', (request) => {
    if (['image', 'stylesheet', 'font'].includes(request.resourceType())) {
        request.abort();
    } else {
        request.continue();
    }
});
Enter fullscreen mode Exit fullscreen mode

Generating Transparent Background Screenshots

For transparent PNGs:

await page.screenshot({ path: 'transparent.png', omitBackground: true });
Enter fullscreen mode Exit fullscreen mode

If the website has a background color, remove it:

await page.evaluate(() => {
    document.body.style.background = 'transparent';
});
Enter fullscreen mode Exit fullscreen mode

Saving Screenshots as Base64

If you need a Base64-encoded screenshot:

const base64 = await page.screenshot({ encoding: 'base64' });
console.log(base64);
Enter fullscreen mode Exit fullscreen mode

Exporting Screenshots as Different Formats

Capture as JPEG:

await page.screenshot({ path: 'screenshot.jpg', type: 'jpeg', quality: 80 });
Enter fullscreen mode Exit fullscreen mode

Capture as WebP:

await page.screenshot({ path: 'screenshot.webp', type: 'webp' });
Enter fullscreen mode Exit fullscreen mode

Using a Proxy with Puppeteer

To route traffic through a proxy:

const browser = await puppeteer.launch({
    args: ['--proxy-server=127.0.0.1:8080'],
});
Enter fullscreen mode Exit fullscreen mode

For per-page proxy, install puppeteer-page-proxy:

npm install puppeteer-page-proxy
Enter fullscreen mode Exit fullscreen mode
const useProxy = require('puppeteer-page-proxy');
await useProxy(page, 'http://yourproxy:8080');
Enter fullscreen mode Exit fullscreen mode

Avoiding Puppeteer Detection

Some sites block Puppeteer scripts. Use stealth mode:

npm install puppeteer-extra puppeteer-extra-plugin-stealth
Enter fullscreen mode Exit fullscreen mode
const puppeteer = require('puppeteer-extra');
const StealthPlugin = require('puppeteer-extra-plugin-stealth');
puppeteer.use(StealthPlugin());
Enter fullscreen mode Exit fullscreen mode

Alternative to Puppeteer: CaptureKit API

Setting up Puppeteer can be complex. If you need a faster, scalable, and maintenance-free solution, consider using for CaptureKit API:

curl "https://api.capturekit.dev/capture?url=https://example.com&access_key=YOUR_ACCESS_KEY"
Enter fullscreen mode Exit fullscreen mode

Benefits of CaptureKit API

  • No need to manage browsers
  • Faster and more reliable
  • Supports full-page, high-resolution, and custom viewport screenshots

Conclusion

Puppeteer provides powerful automation for taking screenshots, but setting it up and maintaining browser instances can be cumbersome. By mastering Puppeteer's options and leveraging tools like CaptureKit API, you can streamline screenshot automation efficiently. 🚀

5 Playwright CLI Flags That Will Transform Your Testing Workflow

  • 0:56 --last-failed
  • 2:34 --only-changed
  • 4:27 --repeat-each
  • 5:15 --forbid-only
  • 5:51 --ui --headed --workers 1

Learn how these powerful command-line options can save you time, strengthen your test suite, and streamline your Playwright testing experience. Click on any timestamp above to jump directly to that section in the tutorial!

Top comments (0)

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more

👋 Kindness is contagious

DEV shines when you're signed in, unlocking a customized experience with features like dark mode!

Okay