UNPKG

playwright-mcp

Version:
88 lines (79 loc) 2.5 kB
import { BrowserEvent, BrowserEventType } from './events.js'; import { getSelectors } from './selector-engine.js'; import { Window } from 'happy-dom'; const parseDom = (html: string) => { const window = new Window({ settings: { disableJavaScriptEvaluation: true, }, }); window.document.write(html); return window.document as unknown as Document; }; export const preprocessBrowserEvent = (event: BrowserEvent) => { if ( event.type === BrowserEventType.Click || event.type === BrowserEventType.Input ) { const dom = parseDom(event.dom); event.selectors = getSelectors(dom, event.elementUUID); const element = dom.querySelector(`[uuid="${event.elementUUID}"]`); event.elementName = element ? getElementName(element) : 'unknown'; event.elementType = element ? getElementType(element) : 'unknown'; // for efficiency, we don't need to preserve it for now event.dom = ''; } }; const extractText = (element: Element): string => { if (element.childNodes.length === 0) { return element.textContent?.trim() || ''; } const texts = Array.from(element.childNodes).map(node => extractText(node as unknown as Element) ); return texts .filter(text => text.trim().length > 0) .map(text => text.trim()) .join('\n'); }; const extractTextsFromSiblings = (element: Element): string[] => { const siblings = Array.from(element.parentElement?.childNodes || []); return siblings .map(sibling => extractText(sibling as unknown as Element)) .map(text => text.trim()) .filter(text => text.length > 0); }; const getElementName = (element: Element) => { let text = ''; const priorityAttrs = ['aria-label', 'title', 'placeholder', 'name', 'alt']; for (const attr of priorityAttrs) { if (!text) { text = element?.getAttribute(attr) || ''; } } if (!text) { text = extractText(element); } if (!text) { text = extractTextsFromSiblings(element).join('\n'); } if (!text) { text = 'unknown'; } return text; }; const getElementType = (element: Element) => { const tagName = element?.tagName.toLowerCase(); let elementType: 'button' | 'link' | 'input' | 'textarea' | 'element' = 'element'; if (tagName === 'a') { elementType = 'link'; } else if (tagName === 'button') { elementType = 'button'; } else if (tagName === 'textarea') { elementType = 'textarea'; } else if (tagName === 'input') { elementType = 'input'; } return elementType; };