Puppeteer Options for Listing Installed Browsers
List browsers in Puppeteer’s managed cache with the CLI or JavaScript API, and learn how that differs from finding system Chrome.
To list browser builds installed in a Puppeteer-managed browser cache, run npx @puppeteer/browsers list. In JavaScript, call getInstalledBrowsers({ cacheDir }) from @puppeteer/browsers. Both inspect a cache directory; they do not scan every browser installed on the computer. For system Chrome, use Puppeteer’s separate channel lookup helper or specify an executable path you already know.
1. List the browsers in the default Puppeteer cache
Run this from a terminal:
npx @puppeteer/browsers list
The CLI lists browsers installed through the package’s browser management system. The official guide documents the list command for this purpose: @puppeteer/browsers guide.
If you want to see available commands or flags for the installed CLI version, use its help output:
npx @puppeteer/browsers --help
When using npx, the package may need to be fetched if it is not already available in the project. To keep the command version consistent across machines, install and pin @puppeteer/browsers in your project, then invoke the local package with npx.
2. List a cache programmatically in Node.js
Use getInstalledBrowsers when application code needs to inspect the browser cache. The function returns a promise of installed-browser records. Each record includes browser type, build ID, executable path, installation root, and platform. The cacheDir option must point to the root of the cache you want to inspect; see the API reference and options reference.
import { getInstalledBrowsers } from '@puppeteer/browsers';
const cacheDir = process.env.PUPPETEER_CACHE_DIR ?? './.cache/puppeteer';
const browsers = await getInstalledBrowsers({ cacheDir });
if (browsers.length === 0) {
console.log(`No browser builds found in ${cacheDir}`);
} else {
for (const browser of browsers) {
console.log({
browser: browser.browser,
buildId: browser.buildId,
executablePath: browser.executablePath,
installationPath: browser.path,
platform: browser.platform,
});
}
}
Save it as list-browsers.mjs, install the dependency with npm install @puppeteer/browsers, and run node list-browsers.mjs. Set PUPPETEER_CACHE_DIR to the actual cache root if it differs from the example. The returned records are the supported way to read installation metadata; the InstalledBrowser constructor is internal, so do not construct these records yourself.
3. Choose the lookup that matches your question
| Question | Use | What it covers |
|---|---|---|
| Which browser builds are in this managed cache? | npx @puppeteer/browsers list or getInstalledBrowsers({ cacheDir }) |
The selected Puppeteer browser cache only. |
| Where is system Chrome for a release channel? | computeSystemExecutablePath or launch({ channel }) |
Known system installation locations for Chrome channels. |
| Where is the browser at a path I already have? | launch({ executablePath }) |
That explicit executable; you are responsible for compatibility. |
getInstalledBrowsers is not a machine-wide browser discovery API. The separate system executable helper resolves a system-wide Chrome installation by release channel at known locations. The browser management guide notes that launching system browsers is supported only for Chrome/Chromium.
4. Check system Chrome separately
For a system Chrome channel, the helper takes a platform and channel. This example prints the stable Chrome executable path; if Chrome is not found at the expected location, the helper throws.
import {
BrowserPlatform,
ChromeReleaseChannel,
computeSystemExecutablePath,
} from '@puppeteer/browsers';
const executablePath = computeSystemExecutablePath({
browser: 'chrome',
channel: ChromeReleaseChannel.STABLE,
platform: BrowserPlatform.CHROMIUM,
});
console.log(executablePath);
Use the platform value appropriate to the current host (for example, determine it with detectBrowserPlatform() rather than hard-coding a platform in cross-platform code). The system lookup answers a different question from cache enumeration. Consult the current API documentation for the release-channel and platform types accepted by the version you have installed.
5. Keep cache configuration aligned
The most common reason a listing appears empty is that the command or API is looking at a different cache directory from the one used for installation. Puppeteer configuration can include cacheDirectory, defaultBrowser, executablePath, and skipDownload; documented environment variables can override some settings. Pass the same cache root to getInstalledBrowsers that your installation process uses. Check your version’s configuration documentation and environment when diagnosing a mismatch.
If your app deliberately installs browsers into a custom directory, provide that exact directory:
const browsers = await getInstalledBrowsers({
cacheDir: '/absolute/path/to/browser-cache',
});
Prefer an absolute path in services and build jobs. A relative path is resolved from the process working directory, which may differ between a terminal, a test runner, a container, and a service manager.
6. Select a listed browser for launch
Once you have a record, use its executable path explicitly if the program needs that particular installed build:
import { getInstalledBrowsers, launch } from '@puppeteer/browsers';
const browsers = await getInstalledBrowsers({ cacheDir: './.cache/puppeteer' });
const chrome = browsers.find((browser) => browser.browser === 'chrome');
if (!chrome) {
throw new Error('No Chrome build found in the configured Puppeteer cache');
}
const process = await launch({
executablePath: chrome.executablePath,
headless: true,
args: [],
});
try {
console.log(`Launched ${chrome.browser} ${chrome.buildId}`);
} finally {
await process.close();
}
This demonstrates selecting and launching a browser through @puppeteer/browsers. If your application uses Puppeteer’s higher-level puppeteer.launch(), provide its documented executablePath option or choose a supported channel as appropriate. Puppeteer warns that it is only guaranteed to work with its bundled browser; an arbitrary executable may be incompatible. See the installation and browser compatibility guidance.
7. Compatibility and version considerations
Browser compatibility depends on the Puppeteer version and browser build. The consulted documentation for Puppeteer 25.12.0 maps that release to Chrome for Testing 154.0.8037.57 and Firefox 156.0.1; those versions can change. Check the live supported browsers table for your installed Puppeteer version before mixing browser sources. Puppeteer documents browser types as Chrome and Firefox, while its system-browser launch limitation is specifically Chrome/Chromium.
For reproducible CI and deployments, pin compatible package versions and install the intended browser build as part of environment setup. Do not assume the newest system browser will match an older Puppeteer release.
8. Troubleshooting
| Symptom | Likely cause | Fix |
|---|---|---|
| The list command returns no entries. | No browser was installed in that package-managed cache, or the command is running with a different cache configuration. | Confirm the install location and cache configuration; run the listing from the same environment and set the matching cache directory when using the API. |
| The JavaScript API returns an empty array. | cacheDir points at the wrong directory, or that cache has no installed browser records. |
Pass the cache root used during installation. Use an absolute path and verify the process environment and working directory. |
| System lookup throws that Chrome was not found. | The requested channel is not installed in a known location for that host. | Install that Chrome channel, use a different installed channel, or provide the explicit executable path if you already know it. |
| The executable exists but launch fails. | The browser build may not be compatible with the Puppeteer version, or the host may lack required runtime dependencies. | Use the browser version associated with your Puppeteer release and follow the official install guidance for the host. |
The code cannot import @puppeteer/browsers. |
The package is not installed in the project or the script/module setup does not match its import syntax. | Install the package in the project and run the example as an ES module (for example, use an .mjs file). Check the package’s Node engine requirement. |
| Local results differ from CI results. | Different cache paths, environment overrides, operating systems, or browser builds are in use. | Log the chosen cache path, returned platform/build ID, and executable path in each environment; align installation and enumeration configuration. |
9. Performance, reliability, and cost
Listing is a local cache inspection operation; the documented API returns metadata records and does not describe it as downloading browsers. It is generally appropriate for startup checks or diagnostics, but avoid rescanning repeatedly in a hot request path when a startup inventory can be reused. The documentation provides no benchmark for listing speed, so measure with your cache size and deployment setup if latency matters.
For reliability, treat an empty result as a configuration or installation state to handle explicitly, and validate that a selected executable still exists before launch if cache cleanup can occur concurrently. In build and deployment workflows, keep the install and list steps in the same environment and make the cache directory explicit. The listing command itself has no per-browser charge; browser downloads consume network, storage, and build time according to your environment.
10. Capture a website without managing a browser binary
If your actual goal is to capture a website image or PDF, you may not need to inspect or install a browser locally. ScreenshotNeo is a website screenshot API and MCP server: a single request can return a PNG, JPEG, WebP, or PDF. The API and available parameters are documented at ScreenshotNeo docs.
Or skip the browser setup
This cURL request saves a WebP screenshot:
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
Python:
import requests
r = requests.get(
"https://api.screenshotneo.com/v1/shot",
params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"},
timeout=90,
)
open("shot.webp", "wb").write(r.content)
Node.js:
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
ScreenshotNeo removes cookie banners, newsletter popups, and chat widgets before the shot; bot checks, blank pages, and failed loads are never billed. Its MCP server lets AI agents take screenshots. The free plan includes 1,000 screenshots a month with no card; paid plans start at $5 for 3,000. Sign up for free.
11. Frequently asked questions
Does the list command show every browser installed on my computer?
No. It lists browser builds managed in the relevant Puppeteer cache. System Chrome lookup is a separate operation.
Can I use the API to find a system Firefox installation?
The documented system executable lookup is for Chrome/Chromium. Cache listing can report installed browser builds in the managed cache.
Should I construct an InstalledBrowser record myself?
No. Its constructor is internal. Use records returned by the installation or listing APIs.
Which browser versions should I install?
Use the compatibility table for the Puppeteer version in your project. The documented mapping changes with releases.


