πŸ’‘ If you like this website, please share it with your friends and network! πŸš€
Back to All Questions
Question 56 of 100
Locators
Advanced

What is the difference between locator() and querySelector()?

The Answer

`locator()` is Playwright's lazy, auto-waiting, strict selector. `querySelector()` (via `page.$`) is an immediate DOM query that returns an `ElementHandle` β€” it does NOT auto-wait and is considered a legacy API.

Deep Dive Explanation

The Playwright team strongly recommends never using `ElementHandle` (the object returned by `page.$`). It's a snapshot of the DOM at a point in time and becomes stale. Locators always re-query the DOM on each action, making them inherently fresh.

example.spec.ts
// locator() - RECOMMENDED (lazy, retries, strict)
const btn = page.locator('button#submit');
await btn.click(); // Waits for button to be actionable

// page.$() - LEGACY (immediate, returns null if not found)
const el = await page.$('button#submit'); // Returns null if not ready yet
if (el) {
  await el.click(); // NO auto-waiting
}

// page.evaluate with querySelector - for reading values only
const value = await page.evaluate(() => {
  return document.querySelector('#output')?.textContent;
});