How to Make an AI Agent Screenshot a Webpage with Browser Extensions Disabled
Use Playwright, Puppeteer, or Chrome headless to capture a webpage without browser extensions. Choose the right approach for fresh pages, logged-in sessions, and full-page shots.
Direct answer: Have the AI agent launch a fresh browser process with Playwright or Puppeteer, open the target page, and save a screenshot through the browser’s page API. Both approaches work without installing or enabling extensions. For a one-off capture, Chrome’s headless --screenshot command is simpler. If the page is already open and logged in, connect to that browser through remote debugging when the environment permits it; launching a fresh browser will not inherit the existing session.
Use a viewport screenshot for what is currently visible, and full-page capture when you need the scrollable page. A screenshot is visual evidence, not proof that every dynamic or lazy-loaded element finished rendering. The examples below show documented API patterns; they are not claims of test runs.
1. Choose the capture approach
| Situation | Good starting point | Why |
|---|---|---|
| The agent can launch a browser and may need scripted waits or interactions | Playwright | Page navigation and screenshot capture are expressed in code; full-page capture is an option. |
| The agent already uses a JavaScript Puppeteer workflow | Puppeteer | Its Page API captures screenshots, and it also supports element screenshots. |
| A simple one-off capture with no scripted interaction | Chrome headless CLI | No automation library is needed for the basic command. |
| The page is already open and authenticated | Remote debugging connection | Can connect to a running Chrome or Edge browser if enabled and allowed by policy. |
Playwright, Puppeteer, and Chrome headless are documented ways to capture without relying on a browser extension. The best fit depends on whether the agent needs a new browser or an existing session, a viewport or full page, and a one-off command or scripted behavior.
2. Capture with Playwright
Install Playwright and its browser runtime according to the official installation guide. Save this as capture.mjs and run it with Node.js:
import { chromium } from 'playwright';
const url = process.argv[2] ?? 'https://example.com';
const browser = await chromium.launch();
try {
const page = await browser.newPage({ viewport: { width: 1280, height: 800 } });
await page.goto(url, { waitUntil: 'load', timeout: 30_000 });
await page.screenshot({ path: 'screenshot.png', fullPage: true });
} finally {
await browser.close();
}
Run node capture.mjs https://example.com. The browser is launched by the script, so it does not depend on the user’s normal browser profile or its extensions. Keep fullPage: true to capture the scrollable page; remove it for the current viewport only. See the Playwright screenshot API for screenshot options.
Wait for page-specific readiness
Navigation reaching load is not a universal signal that a single-page application has finished rendering. If the page has a known ready element, wait for it before capturing:
await page.goto(url, { waitUntil: 'domcontentloaded', timeout: 30_000 });
await page.locator('[data-page-ready="true"]').waitFor({ state: 'visible', timeout: 15_000 });
await page.screenshot({ path: 'screenshot.png', fullPage: true });
Replace the selector with one that actually indicates readiness on the target site. If there is no reliable marker, use a deliberate short delay only when appropriate and understand that it may still miss later content. Full-page capture does not guarantee every lazy-loaded image has been fetched.
3. Capture with Puppeteer
Install Puppeteer following its official installation guide. Save this as capture.mjs:
import puppeteer from 'puppeteer';
const url = process.argv[2] ?? 'https://example.com';
const browser = await puppeteer.launch();
try {
const page = await browser.newPage();
await page.setViewport({ width: 1280, height: 800 });
await page.goto(url, { waitUntil: 'networkidle2', timeout: 30_000 });
await page.screenshot({ path: 'screenshot.png', fullPage: true });
} finally {
await browser.close();
}
Run node capture.mjs https://example.com. Puppeteer’s documented screenshot guide demonstrates navigation followed by Page.screenshot(); its example uses networkidle2. That wait condition is not a guarantee that every dynamic site has finished rendering. For an individual component, locate it and use ElementHandle.screenshot() as documented in the Puppeteer screenshot guide.
Puppeteer passes --disable-extensions by default. Its documentation describes a specific exception: some Chrome policies enforce extensions and can cause launch failure; for that condition, the documented workaround is enableExtensions: true. That workaround enables extensions and therefore does not satisfy a strict extensions-disabled requirement. In a managed environment, check the policy and use an allowed browser setup rather than assuming the exception applies to every machine. See Puppeteer troubleshooting.
4. Use Chrome headless for a one-off capture
Chrome documents this basic command:
chrome --headless --disable-gpu --screenshot https://www.chromestatus.com/
It writes screenshot.png to the current working directory. To set the viewport size, use the documented window-size flag:
chrome --headless --disable-gpu --window-size=1280,1696 --screenshot https://www.chromestatus.com/
Replace the executable name with the Chrome binary path used by your environment if needed. This is convenient for a simple capture. Use an automation API when the agent needs custom readiness checks, interactions, or more control over the capture. See Chrome Headless documentation.
5. Connect to an already-open browser when login state matters
A newly launched browser does not automatically share cookies or authenticated state with a user’s existing browser. When a page must be captured in its current logged-in session, Playwright documents connecting to a running Chrome or Edge channel after remote debugging has been enabled. This depends on browser configuration and whether organizational policy allows remote debugging. Read the Playwright documentation on connecting to a running browser and verify the precise supported setup for your environment.
Keep the connection methods distinct: Playwright also documents an extension-based connection that can reuse sessions, cookies, and installed extensions. That extension connection does not meet a strict requirement that extensions be disabled. If policy disallows remote debugging, use an approved authentication flow in a separate browser context or ask the system owner for the permitted approach; do not assume a fresh browser is logged in.
6. Pick viewport, full-page, or element capture
- Viewport: Capture the visible browser viewport. This is usually the right choice for a visual check of the initial screen.
- Full page: Capture the page’s scrollable extent using Playwright’s
fullPage: trueor Puppeteer’s corresponding screenshot option. Very long pages can produce large images, and lazy-loaded content may need page-specific scrolling or readiness handling. - Element: Capture a component when the task concerns one chart, card, or region. Puppeteer documents
ElementHandle.screenshot(); Playwright supports locator-based screenshot capture in its Page API.
For an AI agent that must act on the page, use browser locators or an accessibility snapshot for structured interaction where appropriate. A screenshot alone communicates appearance, not the semantic role or state of each control.
7. Or skip the browser setup
If the task is to get an image from a URL rather than control a local browser session, ScreenshotNeo is a website screenshot API and MCP server. One GET request returns a PNG, JPEG, WebP, or PDF. The API accepts familiar screenshot parameter names to make switching straightforward. See the ScreenshotNeo API documentation.
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
import requests
r = requests.get(
"https://api.screenshotneo.com/v1/shot",
params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"},
timeout=90,
)
r.raise_for_status()
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
if (!res.ok) throw new Error(`Screenshot request failed: ${res.status}`);
await Bun.write('shot.webp', res);
ScreenshotNeo accepts cookie or consent banners like a visitor and removes more than 60 known consent platforms, newsletter popups, and chat widgets before capture; each step can be turned off. Bot checks or CAPTCHAs, blank pages, timeouts, failed loads, and cache hits cost nothing, and response headers indicate the page verdict and billing status. Its MCP server gives AI agents tools named take_screenshot, get_page_info, and capture_pdf. The free plan includes 1,000 shots per month with no card; paid plans start at $5 for 3,000 shots. Create a free ScreenshotNeo account to get 1,000 screenshots a month with no card.
8. Troubleshooting
| Symptom | Likely cause | What to do |
|---|---|---|
| Browser launch fails | Browser binaries or dependencies are missing, the executable is not available, or managed policy blocks the requested setup. | Install the browser runtime required by the chosen tool, check the executable path and permissions, and inspect the framework’s troubleshooting guide. For Puppeteer, check whether a policy-enforced extension requirement is the documented exception; enabling extensions changes the requirement. |
| Screenshot is blank or shows a loading state | Capture happened before the application rendered, navigation failed, or the page requires authentication. | Check navigation errors and status, verify session requirements, and wait for an application-specific ready selector before capture. |
| Some images are missing | Images may be lazy-loaded or fetched after the chosen readiness condition. | Scroll relevant content into view or wait for the site’s image readiness condition before taking the screenshot. A full-page option alone is not proof that all lazy images loaded. |
| Capture hangs or times out | The page may keep connections open or be slow to load; a broad network-idle condition may never be appropriate. | Set a finite navigation timeout and use a page-specific readiness check instead of treating network idle as universal completion. |
| Image differs between runs | Rendering can vary with operating system, browser version, settings, hardware, power source, and headless mode. | Keep baseline and later captures in the same environment and control the browser version and viewport where possible. |
| Existing login is missing | The script started a separate browser profile. | Use an approved remote-debugging connection to the running browser if available, or arrange an approved authentication flow for the automation context. |
| Output file is not where expected | Relative output paths use the process’s current working directory. | Use an absolute path or inspect the working directory before running the command. |
9. Performance, reliability, and cost
For a single static page, Chrome’s CLI avoids writing an automation script. For repeated captures or pages that need waits and interactions, a persistent automation process can avoid some per-capture setup, while browser lifecycle and page isolation still need deliberate handling. Full-page and high-resolution images use more memory and disk than a viewport capture. Keep image dimensions aligned with the consumer’s needs.
Reliability depends on the site’s loading behavior and the capture environment. Use explicit timeouts, verify that navigation succeeded, wait on meaningful page state, and close the browser in a finally block so failures do not leave processes running. For visual comparisons, control the operating system, browser version, viewport, and headless settings; documented browser rendering can vary across environments.
The DIY options above are browser software and do not have a per-screenshot price stated in the cited documentation. Account for the machine and runtime you operate, and check the current terms of any hosting environment. ScreenshotNeo pricing is free for 1,000 shots monthly, then Starter $5 for 3,000, Growth $15 for 15,000, Pro $39 for 60,000, Scale $99 for 250,000, and Business $249 for 1,000,000; yearly billing gives two months free, and every feature is on every plan. Check the product site for current plan details.
10. FAQ
Does disabling extensions prevent screenshots?
No. Browser page screenshot APIs and Chrome’s headless screenshot command capture rendered pages without needing an extension.
Will a fresh Playwright browser use my normal Chrome login?
No. A fresh browser context does not automatically inherit the existing browser’s cookies or logged-in state.
Does full-page capture guarantee every page image is loaded?
No. Lazy loading and application-specific rendering may require scrolling or waiting for a site-specific readiness signal.
Can I use an AI agent without installing a browser extension?
Yes. The agent can call a browser automation script or a screenshot API. For URL-based captures, ScreenshotNeo also offers an MCP server for compatible AI agents.


