Use puppeteer-core in browser extensions via chrome.debugger API
npm install puppeteer-chrome-debugger-transportUse puppeteer-core in your browser extension's background page or service worker. This package provides a transport layer that uses Chrome's chrome.debugger extension API to communicate with the Chrome DevTools Protocol.
- ✨ Use Puppeteer in browser extensions
- 🔌 Built on Chrome's native debugger API
- 🚀 Works in both Manifest V2 and V3 extensions
- 📦 Lightweight with minimal dependencies
- 🎯 Full TypeScript support
``bash`
npm install puppeteer-chrome-debugger-transport puppeteer-core
Your extension must have the debugger permission in manifest.json:
json
{
"permissions": [
"debugger",
"tabs"
]
}
`$3
`json
{
"permissions": [
"debugger",
"tabs"
]
}
`Usage
$3
`javascript
import puppeteer from 'puppeteer-core/lib/cjs/puppeteer/web'
import { ExtensionDebuggerTransport } from 'puppeteer-chrome-debugger-transport'async function run(tabId) {
// Create transport connected to the tab
const extensionTransport = await ExtensionDebuggerTransport.create(tabId)
// Connect puppeteer using the transport
const browser = await puppeteer.connect({
transport: extensionTransport,
defaultViewport: null,
})
// Use first page from pages instead of using browser.newPage()
const [page] = await browser.pages()
await page.goto('https://wikipedia.org')
// Take a screenshot
const screenshot = await page.screenshot({
encoding: 'base64',
});
console.log(
data:image/png;base64,${screenshot}) // Interact with the page
const englishButton = await page.waitForSelector('#js-link-box-en > strong')
await englishButton.click()
const searchBox = await page.waitForSelector('#searchInput');
await searchBox.type('telephone')
await page.keyboard.press('Enter')
// Clean up
await page.close();
}
// Create a new tab and run automation
chrome.tabs.create(
{
active: true,
url: 'https://www.google.co.in',
},
tab => (tab.id ? run(tab.id) : null)
)
`$3
You can also attach to an existing tab:
`javascript
// Get the active tab
chrome.tabs.query({ active: true, currentWindow: true }, async (tabs) => {
if (tabs[0]?.id) {
await run(tabs[0].id);
}
});
`$3
`javascript
async function runWithErrorHandling(tabId) {
try {
const extensionTransport = await ExtensionDebuggerTransport.create(tabId)
const browser = await puppeteer.connect({
transport: extensionTransport,
defaultViewport: null,
}) const [page] = await browser.pages()
await page.goto('https://example.com')
// Your automation code here
} catch (error) {
console.error('Automation failed:', error)
}
}
`API
$3
####
static async create(tabId: number): PromiseCreates and initializes a new transport instance connected to the specified tab.
Parameters:
-
tabId (number): The Chrome tab ID to attach the debugger toReturns: Promise that resolves to an initialized
ExtensionDebuggerTransport instanceThrows: Error if the debugger fails to attach
####
send(message: string): voidSends a Chrome DevTools Protocol command. This is called internally by Puppeteer.
####
close(): voidCloses the debugger connection and cleans up resources.
Important Notes
$3
When using this transport, you should not call
browser.newPage(). Instead, use the existing page:`javascript
// ✅ Correct
const [page] = await browser.pages()// ❌ Incorrect
const page = await browser.newPage()
`$3
The debugger attaches to a specific tab. If the tab is closed, the connection will be terminated.
$3
Make sure your extension has the
debugger permission, otherwise the connection will fail.$3
This package only works in Chrome/Chromium-based browser extensions that support the
chrome.debugger API.Limitations
- Only works in Chrome/Chromium-based browsers
- Requires the
debugger permission
- Cannot create new tabs via browser.newPage()` (must use existing tabs)Check out the examples directory for more use cases:
- Basic automation
- Screenshot capture
- Form filling
- Web scraping in extensions
MIT
Contributions are welcome! Please feel free to submit a Pull Request.
If you encounter any issues or have questions, please open an issue on GitHub.