@zorilla/puppeteer-extra-plugin-devtools
v1.0.1
Published
Make puppeteer browser debugging possible from anywhere (devtools with screencasting on the internet).
Maintainers
Readme
@zorilla/puppeteer-extra-plugin-devtools
A plugin for
puppeteer-extraandplaywright-extra.
Installation
npm install @zorilla/puppeteer-extra-plugin-devtoolsPurpose
Make puppeteer browser debugging possible from anywhere.
- Creates a secure tunnel to make the devtools frontend (incl. screencasting) accessible from the public internet
- Works for both headless and headful puppeteer instances, as well as within docker containers
- Uses the already existing DevTools Protocol websocket connection from puppeteer
- Features some convenience functions for using the devtools frontend locally
- Compatible with both Puppeteer and Playwright through
puppeteer-extraandplaywright-extra
Magic

Quickstart
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
const devtools = devtoolsPlugin();
puppeteer.use(devtools);
const browser = await puppeteer.launch({ headless: true });
const tunnel = await devtools.createTunnel(browser);
console.log('DevTools URL:', tunnel.url);
const page = await browser.newPage();
await page.goto('https://example.com');
console.log('All setup. Access DevTools at:', tunnel.url);TypeScript Support
This plugin is written in TypeScript and includes full type definitions. No additional @types package is needed.
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
import type { Browser } from 'puppeteer';
const devtools = devtoolsPlugin({
auth: { user: 'admin', pass: 'secret123' },
prefix: 'my-devtools',
});
puppeteer.use(devtools);
const browser: Browser = await puppeteer.launch();
const tunnel = await devtools.createTunnel(browser);API
Plugin
Extends: PuppeteerExtraPlugin
As the tunnel page is public, the plugin requires basic auth.
You can set your own credentials using opts or setAuthCredentials().
If you don't specify basic auth credentials, the plugin will generate a password and print it to STDOUT.
Options
interface PluginOptions {
auth?: {
user: string;
pass: string;
};
prefix?: string;
localtunnel?: object;
}auth.user- Username for basic auth (default:'user')auth.pass- Password for basic auth (will be generated if not provided)prefix- The prefix to use for the localtunnel.me subdomain (default:'devtools-tunnel')localtunnel- Advanced options to pass to localtunnel
Example:
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
const devtools = devtoolsPlugin({
auth: { user: 'francis', pass: 'president' },
});
puppeteer.use(devtools);
const browser = await puppeteer.launch();
console.log('Tunnel URL:', (await devtools.createTunnel(browser)).url);
// => Tunnel URL: https://devtools-tunnel-n9aogqwx3d.localtunnel.mecreateTunnel(browser)
Create a new public tunnel.
Supports multiple browser instances (will create a new tunnel for each).
Parameters:
browser- The browser instance to create the tunnel for
Returns: Promise<Tunnel> - The Tunnel instance
Example:
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
const devtools = devtoolsPlugin();
devtools.setAuthCredentials('bob', 'swordfish');
puppeteer.use(devtools);
const browserFleet = await Promise.all(
[...Array(3)].map(() => puppeteer.launch())
);
for (const [index, browser] of browserFleet.entries()) {
const { url } = await devtools.createTunnel(browser);
console.info(`Browser ${index}'s devtools: ${url}`);
}
// =>
// Browser 0's devtools: https://devtools-tunnel-fzenb4zuav.localtunnel.me
// Browser 1's devtools: https://devtools-tunnel-qe2t5rghme.localtunnel.me
// Browser 2's devtools: https://devtools-tunnel-pp83sdi4jo.localtunnel.mesetAuthCredentials(user, pass)
Set the basic auth credentials for the public tunnel page.
Alternatively, the credentials can be defined when instantiating the plugin.
Parameters:
user- Usernamepass- Password
Returns: this - For method chaining
Example:
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
const devtools = devtoolsPlugin();
puppeteer.use(devtools);
const browser = await puppeteer.launch();
devtools.setAuthCredentials('bob', 'swordfish');
const tunnel = await devtools.createTunnel(browser);getLocalDevToolsUrl(browser)
Convenience function to get the local devtools frontend URL.
Parameters:
browser- The browser instance
Returns: string - The local DevTools URL
Example:
import puppeteer from '@zorilla/puppeteer-extra';
import devtoolsPlugin from '@zorilla/puppeteer-extra-plugin-devtools';
const devtools = devtoolsPlugin();
puppeteer.use(devtools);
const browser = await puppeteer.launch();
console.log(devtools.getLocalDevToolsUrl(browser));
// => http://localhost:55952Tunnel
Extends: RemoteDevTools.DevToolsTunnel
The devtools tunnel for a browser instance.
tunnel.url
Get the public devtools frontend URL.
Type: string
Example:
const tunnel = await devtools.createTunnel(browser);
console.log(tunnel.url);
// => https://devtools-tunnel-sdoqqj95vg.localtunnel.metunnel.getUrlForPage(page)
Get the devtools frontend deep link for a specific page.
Parameters:
page- The page instance
Returns: string - The DevTools URL for the specific page
Example:
const page = await browser.newPage();
const tunnel = await devtools.createTunnel(browser);
console.log(tunnel.getUrlForPage(page));
// => https://devtools-tunnel-bmkjg26zmr.localtunnel.me/devtools/inspector.html?ws=...tunnel.close()
Close the tunnel.
The tunnel will automatically stop when your script exits.
Returns: this - For method chaining
Example:
const tunnel = await devtools.createTunnel(browser);
// ... do work ...
tunnel.close();Security Considerations
- The tunnel creates a publicly accessible endpoint protected by basic auth
- Generated passwords are 40 characters long and cryptographically random
- Always use HTTPS for the tunnel connection (handled automatically by localtunnel)
- Consider using custom credentials for production use
- The tunnel exposes your browser's DevTools Protocol - only use in trusted environments
Troubleshooting
Tunnel Connection Issues
If you're having trouble connecting to the tunnel:
- Check that port forwarding is working correctly
- Verify basic auth credentials
- Ensure localtunnel service is operational
- Check firewall settings
Local DevTools
For local development, you can use getLocalDevToolsUrl() instead of creating a tunnel:
const localUrl = devtools.getLocalDevToolsUrl(browser);
console.log('Local DevTools:', localUrl);
// Open this URL in your browser to debug locallyLicense
Contributing
See the main zorilla repository for contribution guidelines.
