diff --git a/playwriter/src/mcp.ts b/playwriter/src/mcp.ts index 8754e40..cfea736 100644 --- a/playwriter/src/mcp.ts +++ b/playwriter/src/mcp.ts @@ -88,6 +88,9 @@ const MAX_LOGS_PER_PAGE = 5000 // Store last accessibility snapshot per page for diff feature const lastSnapshots: WeakMap = new WeakMap() +// Cache CDP sessions per page +const cdpSessionCache: WeakMap = new WeakMap() + const RELAY_PORT = 19988 const LOG_FILE_PATH = process.env.PLAYWRITER_LOG_PATH || path.join(os.tmpdir(), 'playwriter-relay-server.log') const NO_TABS_ERROR = `No browser tabs are connected. Please install and enable the Playwriter extension on at least one tab: https://chromewebstore.google.com/detail/playwriter-mcp/jfeammnjpkecdekppnclgkkffahnhfhe` @@ -536,8 +539,14 @@ server.tool( } const getCDPSession = async (options: { page: Page }) => { + const cached = cdpSessionCache.get(options.page) + if (cached) { + return cached + } const wsUrl = getCdpUrl({ port: RELAY_PORT }) - return getCDPSessionForPage({ page: options.page, wsUrl }) + const session = await getCDPSessionForPage({ page: options.page, wsUrl }) + cdpSessionCache.set(options.page, session) + return session } let vmContextObj: VMContextWithGlobals = { diff --git a/playwriter/src/prompt.md b/playwriter/src/prompt.md index 9af2988..18ca5f6 100644 --- a/playwriter/src/prompt.md +++ b/playwriter/src/prompt.md @@ -89,12 +89,18 @@ you have access to some functions in addition to playwright methods: - `minWait`: (optional) minimum wait before checking in ms (default: 500) - Returns: `{ success, readyState, pendingRequests, waitTimeMs, timedOut }` - Filters out: ad networks (doubleclick, googlesyndication), analytics (google-analytics, mixpanel, segment), social (facebook.net, twitter), support widgets (intercom, zendesk), and slow fonts/images -- `getCDPSession({ page })`: creates a CDP session to send raw Chrome DevTools Protocol commands. Use this instead of `page.context().newCDPSession()` which does not work through the playwriter relay. +- `getCDPSession({ page })`: creates a CDP session to send raw Chrome DevTools Protocol commands. Use this instead of `page.context().newCDPSession()` which does not work through the playwriter relay. Sessions are cached per page. - `page`: the page object to create the session for - - Returns: `{ send(method, params?), on(event, callback), off(event, callback), detach() }` - - Example: `const cdp = await getCDPSession({ page }); const metrics = await cdp.send('Page.getLayoutMetrics'); cdp.detach();` - -To bring a tab to front and focus it, use the standard Playwright method `await page.bringToFront()` + - Returns: `{ send(method, params?), on(event, callback), off(event, callback) }` + - Example: `const cdp = await getCDPSession({ page }); const metrics = await cdp.send('Page.getLayoutMetrics');` + - Example listening for events: + ```js + const cdp = await getCDPSession({ page }); + await cdp.send('Debugger.enable'); + const pausedEvent = await new Promise((resolve) => { cdp.on('Debugger.paused', resolve); }); + console.log('Paused at:', pausedEvent.callFrames[0].location); + await cdp.send('Debugger.resume'); + ``` example: