Listen for Puppeteer’s requestfailed event and log the request URL plus request.failure()?.errorText. Then check whether you have a transport/loading failure, an HTTP error such as 404, or a separate navigation timeout—those are different problems and require different diagnostics.
Log failed requests before triggering them
Attach the listener before page.goto() or whatever interaction starts the request. Puppeteer’s HTTPRequest.failure() documentation shows logging the URL and failure text. In production, guard against a missing failure object or missing error text:
As an Amazon Associate I earn from qualifying purchases.
page.on('requestfailed', request => {
const failure = request.failure();
console.error(
'Request failed:',
request.url(),
failure?.errorText ?? '(no failure text)'
);
});
A failure text such as net::ERR_FAILED can help identify the cause, but Puppeteer does not guarantee that text will be present. Keep the URL in your logs and correlate it with browser output, server logs, and the action that initiated the request.
Tell request failures apart from HTTP error statuses
requestfailed means the request did not complete successfully at the loading or transport level. It does not mean every response with an unsuccessful HTTP status. In Puppeteer’s documented request lifecycle, a request proceeds from request to either requestfinished or requestfailed. An HTTP response such as 404 or 503 is still a completed request and normally emits requestfinished; inspect its response and status code instead. See the Puppeteer API reference.
#1 Best Overall
If your page loads but displays an error page or unexpected content, log responses as well as failures:
page.on('response', response => {
if (response.status() >= 400) {
console.error('HTTP error:', response.status(), response.url());
}
});
This response listener is a useful way to find HTTP statuses; it does not replace the requestfailed listener for loading failures.
Rank #2
Diagnose a rejected page.goto()
A navigation rejection has several possible causes, not all of which appear as a useful failed-request message. The documented Frame.goto() behavior includes these cases:
- The target URL is invalid.
- An SSL error prevents navigation.
- The navigation timeout is exceeded.
- The server cannot be reached or does not respond.
- The main resource fails to load.
- A configured URL allowlist or blocklist prevents access.
Check the exact URL, the browser’s error output, the target server’s availability, and any URL access rules used by your setup. If navigation follows redirects and resolves, Puppeteer returns the response for the last redirect, not an earlier redirect in the chain.
Find which timeout expired
Do not raise every timeout as a first response. Identify the operation that timed out: navigation, waiting for a selector, waiting for navigation after an action, or another wait. Puppeteer provides navigation timeout controls for operations including goto, reload, back/forward, setContent, and waitForNavigation. The WaitForOptions reference documents a 30,000 ms default for its wait timeout; setting it to 0 disables that timeout. Page timeout methods can also change defaults.
Increase a timeout only when the operation is genuinely slow and a longer wait is appropriate. Disabling a timeout can leave a script waiting indefinitely, so use it only when that behavior is intended.
Rank #4
Work through the failure by symptom and scope
- One request fails: Start with its URL and failure text, then check whether it is the main document or a subresource such as an image or script.
- The request completed but the page is wrong: Inspect response statuses; a 404 or 503 is an HTTP result, not a
requestfailedevent. - Navigation rejects: Check URL validity, SSL, reachability, the main resource, timeout settings, and URL access rules.
- Only later page interaction fails: Determine whether a selector or other wait expired rather than assuming the original navigation failed.
- Many URLs fail only in CI, a container, or cloud: Investigate the browser installation and runtime environment as well as the target sites.
Puppeteer’s troubleshooting guide covers environment-specific examples, including package-manager restrictions that affect browser downloads, HTTPS-first behavior that can make remote HTTP navigation report net::ERR_BLOCKED_BY_CLIENT, Linux sandbox or AppArmor launch problems, and Alpine Chromium compatibility caveats. Match the documented issue to your actual error and runtime. Do not disable the browser sandbox as a blanket fix; doing so changes the security posture.
Or skip the browser setup
If your task is to capture a website rather than debug your Puppeteer runtime, ScreenshotNeo offers a screenshot API and MCP server for developers. A single GET request can return a PNG, JPEG, WebP, or PDF. For example, use cURL to save a WebP screenshot:
Quick Recap
Best Value
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
See the ScreenshotNeo documentation for request options and response details. ScreenshotNeo removes cookie banners, newsletter popups, and chat widgets before capture; bot checks, blank pages, failed loads, and cache hits are not billed. Its MCP server gives AI agents tools to take screenshots, get page information, and capture PDFs. The Free plan includes 1,000 screenshots a month with no card; paid plans start at $5 for 3,000 shots. Sign up for free.
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.




