How to Capture Screenshots Behind a Login Wall

Taking screenshots of public pages is easy. But what happens when you need an automated snapshot of a private analytics dashboard, user profile, or protected report? Learn how to navigate login walls reliably.

📋 Table of Contents

Why Authentication is Tricky

Most basic screenshot tools use a fresh, stateless browser session every time they run. This means when they visit app.yourcompany.com/dashboard, they don't see the dashboard — they see the login screen!

To capture protected content, your screenshot automation must either simulate a real user logging in or adopt the identity of an already authenticated user.

Let's look at the three primary ways developers solve this.

Method 1: Injecting Cookies / Tokens

The most reliable, performance-friendly way to bypass a login page is to inject an active session cookie or LocalStorage token directly into the browser context before calling the page load.

Here's how you do it using Puppeteer:

import puppeteer from 'puppeteer';

(async () => {
    const browser = await puppeteer.launch();
    const page = await browser.newPage();
    
    // Inject your authentication cookie
    const cookies = [{
      name: 'session_id',
      value: 'your_secure_session_token_12345',
      domain: '.example.com',
      path: '/',
      httpOnly: true,
      secure: true
    }];
    
    await page.setCookie(...cookies);
    
    // Now you bypass the login and go straight to the protected page
    await page.goto('https://app.example.com/dashboard');
    
    await page.screenshot({ path: 'dashboard.png', fullPage: true });
    await browser.close();
})();

Pros: Extremely fast since you skip the UI login flow.
Cons: You need an existing backend mechanism to issue or retrieve active session tokens programmatically.

Method 2: Automating Form Submission

If you cannot generate authenticating cookies directly, you must instruct the headless browser to type in the credentials and click the login button, just like a human.

Here is an example using Playwright in Python:

from playwright.sync_api import sync_playwright

with sync_playwright() as p:
    browser = p.chromium.launch()
    page = browser.new_page()
    
    # 1. Go to the login page
    page.goto('https://app.example.com/login')
    
    # 2. Fill in credentials and submit
    page.fill('input[name="email"]', '[email protected]')
    page.fill('input[name="password"]', 'SuperSecret123!')
    page.click('button[type="submit"]')
    
    # 3. Wait for the transition to the dashboard
    page.wait_for_url('https://app.example.com/dashboard')
    
    # 4. Take the screenshot
    page.screenshot(path="auth_dashboard.png", full_page=True)
    browser.close()

Pros: Simulates an exact user flow; doesn't require direct backend database access.
Cons: Much slower. Very fragile if the login page implements CAPTCHAs, bot protection (like Cloudflare), or Two-Factor Authentication (2FA).

Method 3: HTTP Basic Authentication

Sometimes you need to screenshot a staging site protected simply by a browser-native username and password prompt (HTTP Basic Auth or htpasswd).

This is easily bypassed by supplying credentials directly in the URL (https://user:[email protected]) or via headers:

import puppeteer from 'puppeteer';

(async () => {
    const browser = await puppeteer.launch();
    const page = await browser.newPage();
    
    // Provide Basic Auth credentials
    await page.authenticate({
        username: 'admin',
        password: 'password123'
    });
    
    await page.goto('https://staging.example.com');
    await page.screenshot({ path: 'staging.png' });
    await browser.close();
})();

The Easiest Way: Using a Managed API

If you're building a feature that takes screenshots at scale, managing headless browsers and dealing with login state timing issues becomes a massive headache.

With SnapAPI, you can pass headers or cookies in a simple HTTP request, and our infrastructure handles the heavy lifting, taking the screenshot seamlessly behind your authentication barrier.

curl -X POST "https://snapapi.alterra-solutions.com/v1/capture" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer YOUR_SNAPAPI_KEY" \
  -d '{
    "url": "https://app.example.com/dashboard",
    "cookies": "session_id=your_secure_session_token",
    "headers": {
      "Authorization": "Bearer internal_api_token"
    },
    "full_page": true
  }' -o secure_dashboard.png

Conclusion

Capturing authenticated pages requires a strategy. If you have API access to issue tokens, injecting cookies is the most robust path. If not, automating the form ensures a real-world flow. For production scale, rely on a dedicated API to manage the browser complexities for you.

Securely Capture Private Dashboards

SnapAPI supports injecting cookies and custom headers, making authenticated screenshots effortless.

Start Capturing Today →