When I add "selectorName" selector for "xpathSelector" xpath selector

This step registers a named XPath selector in the current scenario's XPath registry at runtime. The first argument is the human-readable name; the second is an XPath expression. The expression may start with xpath= or with // - the step normalises both forms by prepending xpath= when needed before passing the locator to Playwright.

XPath selectors are resolved after CSS selectors when both registries contain the same name - the CSS entry wins. Inline XPath registrations override pre-loaded entries of the same name; the last When I add call in a scenario wins. XPath is especially useful for elements that are easier to identify by text content or structural position than by class or attribute, such as the last item in a navigation list or any element whose rendered label contains a specific string.

Accepted phrasings

When I add "NAME" selector for "XPATH" xpath selector
When we add "NAME" selector for "XPATH" xpath selector
And I add "NAME" selector for "XPATH" xpath selector
And we add "NAME" selector for "XPATH" xpath selector

Examples

When I add "page title" selector for "//h1[contains(@class,'page-header')]" xpath selector
When I add "active tab" selector for "//li[contains(@class,'active')]/a" xpath selector
When I add "first table row" selector for "//table/tbody/tr[1]" xpath selector
When I add "login link" selector for "//a[contains(normalize-space(.),'Login')]" xpath selector

In a real scenario

Scenario: Active navigation tab is visible above the content area
  Given I navigate to "https://example.org/dashboard"
  And I define css selectors:
    | content area | .main-content |
  When I add "active tab" selector for "//li[contains(@class,'active')]/a" xpath selector
  And I add "first heading" selector for "//h1[1]" xpath selector
  Then I see visible active tab, first heading, content area
  And I see active tab above content area

Related steps

Back to Selectors Steps