{"record":{"id":"03c84755c907f112","repo":"microsoft/playwright","slug":"unable-to-generate-locator-for-selector","errorCode":null,"errorMessage":"Unable to generate locator for ${selector}","messagePattern":"Unable to generate locator for (.+?)","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/playwright-core/src/server/frames.ts","lineNumber":1320,"sourceCode":"\n  async focus(progress: Progress, selector: string, options: types.StrictOptions & { noAutoWaiting?: boolean }) {\n    dom.assertDone(await this._retryWithProgressIfNotConnected(progress, selector, options, (progress, handle) => handle._focus(progress)));\n  }\n\n  async blur(progress: Progress, selector: string, options: types.StrictOptions & { noAutoWaiting?: boolean }) {\n    dom.assertDone(await this._retryWithProgressIfNotConnected(progress, selector, options, (progress, handle) => handle._blur(progress)));\n  }\n\n  async resolveSelector(progress: Progress, selector: string, options: { mainWorld?: boolean } = {}): Promise<{ resolvedSelector: string }> {\n    const element = await progress.race(this.selectors.query(selector, options));\n    if (!element)\n      throw new Error(`No element matching ${selector}`);\n\n    const generated = await progress.race(element.evaluateInUtility(async ([injected, node]) => {\n      return injected.generateSelectorSimple(node as unknown as Element);\n    }, {}));\n    if (!generated)\n      throw new Error(`Unable to generate locator for ${selector}`);\n\n    let frame: Frame | null = element._frame;\n    const result = [generated];\n    while (frame?.parentFrame()) {\n      const frameElement = await frame.frameElement(progress);\n      if (frameElement) {\n        const generated = await progress.race(frameElement.evaluateInUtility(async ([injected, node]) => {\n          return injected.generateSelectorSimple(node as unknown as Element);\n        }, {}));\n        frameElement.dispose();\n        if (generated === 'error:notconnected' || !generated)\n          throw new Error(`Unable to generate locator for ${selector}`);\n        result.push(generated);\n      }\n      frame = frame.parentFrame();\n    }\n    const resolvedSelector = result.reverse().join(' >> internal:control=enter-frame >> ');\n    return { resolvedSelector };","sourceCodeStart":1302,"sourceCodeEnd":1338,"githubUrl":"https://github.com/microsoft/playwright/blob/c8fc3bf8d31542d59b4d4d9eaab1df93ff541dc6/packages/playwright-core/src/server/frames.ts#L1302-L1338","documentation":"Thrown by Frame.resolveSelector() when the generateSelectorSimple() injected script returns a falsy value for the matched element itself (not its parent frames). This means Playwright's selector generation engine could not produce a valid CSS/XPath selector for the element, which can happen with elements that lack distinguishing attributes or are in unusual DOM positions.","triggerScenarios":"Calling resolveSelector on an element that the selector generator cannot describe. This occurs when the element is deeply nested in a generic DOM structure with no unique attributes, or when the element's structure is too dynamic for the generator to produce a stable selector.","commonSituations":"Element is a bare <div> or <span> with no id, class, or data attributes among many siblings. Shadow DOM or custom elements that confuse the generator. Element was detached between the query and the generateSelector call.","solutions":["Add a stable identifier (id, data-testid) to the element in the page's HTML so the generator can target it.","Use a hand-written selector instead of relying on resolveSelector's auto-generation.","If using MCP tools, specify the selector explicitly rather than relying on resolution."],"exampleFix":"// before — element has no distinguishing attributes\n<button>Submit</button>\n// resolveSelector fails to generate a locator\n\n// after — add a data-testid\n<button data-testid=\"submit-btn\">Submit</button>","handlingStrategy":"validation","validationCode":"// Add data-testid to elements to ensure reliable selector generation\n// In page HTML: <div data-testid=\"my-element\">","typeGuard":null,"tryCatchPattern":"try {\n  await frame.resolveSelector(selector);\n} catch (e) {\n  if (e.message.startsWith('Unable to generate locator')) {\n    // Provide a hand-crafted selector instead\n    return { resolvedSelector: manualSelector };\n  }\n  throw e;\n}","preventionTips":["Add data-testid attributes to elements for stable selector generation.","Provide explicit selectors instead of relying on auto-generation for complex DOMs.","Ensure elements have distinguishing attributes (id, role, data-*)."],"tags":["resolveselector","selector-generation","locator","frame"],"backgroundTag":null,"analyzedSha":"c8fc3bf8d31542d59b4d4d9eaab1df93ff541dc6","analyzedAt":"2026-08-12T07:26:36.950Z","schemaVersion":2},"datasetVersion":"2026-08-12T13:17:24.610Z"}