Playwright Locators and Selectors: How to Find Elements That Don't Break
The way you locate elements is the single biggest factor in whether your tests survive UI changes. Here's how Playwright locators work and which selectors to prefer.
Alex Johnson
TL;DR
A locator is a resilient, re-evaluated description of how to find an element. Playwright recommends user-facing locators — by role, label, text, and test IDs — over brittle CSS or XPath tied to styling. Choosing the right locators is the most effective way to prevent tests from breaking on routine design changes.
How you tell a test to find an element — the button, the input, the heading — is the single biggest factor in whether that test survives everyday UI changes. Get it right and your tests keep passing through redesigns. Get it wrong and they break every sprint. This is how locators and selectors work in Playwright, and which to choose.
Selector vs. locator: what's the difference?
A selector is the string that describes how to find an element — a CSS query, a text match, a role. A locator is the Playwright object you build from that description. The distinction matters: a locator is lazy and re-evaluated every time you use it, and it carries built-in auto-waiting. So a locator always acts on the element as it exists right now, rather than a stale snapshot captured earlier — a major reliability win over older approaches.
Prefer user-facing locators
Playwright's guiding principle is to find elements the way a real user (or a screen reader) perceives them, not by internal implementation details. In rough order of preference:
- By role — find a "button named Sign in" or a "heading named Dashboard." This mirrors how assistive technology sees the page and is the most robust option.
- By label, placeholder, or text — ideal for form fields and visible content a user reads.
- By test ID — an explicit attribute you add (like
data-testid) for elements that lack stable user-facing attributes. Reliable because it exists purely for testing and won't change with styling.
What to avoid
Brittle selectors are the leading cause of tests that break for no real reason:
- CSS classes tied to styling — a class like
.btn-primary-lgchanges the moment a designer adjusts the look, even though the feature still works. - Deep DOM paths — selectors like
div > div > span:nth-child(3)break if anyone adds a wrapper element anywhere above. - Auto-generated IDs — framework-generated identifiers often change between builds.
When a test finds elements this way, a routine design change cascades into dozens of failures — a classic source of flaky-feeling breakage that erodes trust in the suite.
Filtering and chaining
Real pages have repeated elements — ten "Add to cart" buttons, a row per order. Locators can be narrowed by filtering on text or by chaining within a parent ("the Add to cart button inside the row that contains 'Wireless Mouse'"). This lets you write precise, readable locators without resorting to fragile positional selectors.
Let the tooling help
You do not have to choose locators by hand. Playwright's Codegen records your clicks and automatically picks resilient, user-facing locators, and its inspector can suggest a good locator for any element you point at. It is an excellent way to learn the patterns and avoid brittle habits.
The takeaway
Resilient locators are the highest-leverage habit in E2E testing: they are why one suite sails through a redesign while another breaks every release. Favor role, label, and text; reserve test IDs for the gaps; and avoid styling-based selectors entirely. QA Guardian builds every test on stable, user-facing locators so your coverage survives UI changes — and you own the standard Playwright code. Book a demo to see it on your app.
Frequently asked questions
What is the difference between a locator and a selector in Playwright?
A selector is the string that describes how to find an element (for example, a CSS or text query). A locator is a Playwright object built from a selector that is re-evaluated every time it is used and carries built-in auto-waiting, which makes it far more reliable than a one-time element handle.
What is the best locator to use in Playwright?
Prefer user-facing locators in this rough order: by role (getByRole), by label or placeholder for form fields, by visible text, and by an explicit test ID (getByTestId) for elements without stable user-facing attributes. Avoid CSS classes or deep DOM paths tied to styling.
Tags
More on Playwright
What Is Playwright? A Plain-English Guide to Modern Browser Testing
Playwright is an open-source framework for automating web browsers to test that your app works the way real users expect. Here's what it is, who it's for, and why teams are adopting it.
How Playwright Works: Architecture, Auto-Waiting, and the Test Lifecycle
Under the hood, Playwright communicates with browsers over a single WebSocket connection and waits for elements to be actionable automatically. Here's how that architecture produces fast, reliable tests.
Playwright vs. Selenium: Which Browser Automation Framework Should You Use?
Selenium defined browser automation for a decade. Playwright is the modern alternative. Here is a neutral comparison of their architectures, speed, browser support, and when to migrate.
See modern QA in action
Everything we write about is what we build and run every day. Book a demo and we'll show you flow-based Playwright coverage on your own codebase.