What does Selenium's WebElement.getAriaRole() return, and how does it differ from reading the role attribute?
answer
- Two different questions about one element
- Template token versus browser computation
- Implicit roles count too
- A dedicated command, not injected script
- Its sibling returns the announced name
basics
~20 sIt returns the WAI-ARIA role the browser computed for the element, including the implicit role of the tag. Reading the role attribute returns only the literal token the markup declared, or nothing when the markup declared none.
solid answer
~30 s`getAriaRole()` returns the element's computed WAI-ARIA role as a `String`, so a plain `<button>` on a route planner's dispatch board reports `button` even with no `role` attribute in its markup, and a `<div role="button">` reports `button` too. `getDomAttribute("role")` is the other read: it returns the literal token the template wrote, or `null`. The computed value comes from a dedicated W3C WebDriver command, `GET .../element/{id}/computedrole`, and the computation is the browser's, not Selenium's. Its sibling `getAccessibleName()` issues `.../computedlabel` and returns the name assistive technology would announce. Both were added in Selenium 4 and are `default` methods on `WebElement` that `RemoteWebElement` implements.
go deeper
Recall that Selenium can ask an element for its ARIA role and its accessible name, and that these are reads on an element you have already found rather than ways of finding one.
Explain the difference between the computed role and the role attribute, and name what each returns for a plain button element whose markup carries no role at all.
Show where the computed read earns its cost: a control whose markup shape changes between refactors still reports the same role, so the check follows what the widget exposes rather than how it happens to be built.
Own the limits. The value is the browser's computation, so it can differ across browsers, and treating a passing role read as an accessibility guarantee is a claim the suite cannot support.
## What the call returns `WebElement.getAriaRole()` returns the element's **computed WAI-ARIA role**: the role the browser resolved for that element, as a `String`. On a courier route planner's dispatch board, a plain `<button id="optimise-route">` returns `button` even though its markup carries no `role` attribute at all, because `button` is that tag's implicit role. Selenium 4 added the call together with its sibling `WebElement.getAccessibleName()`, which returns the element's computed accessible name — the text an assistive technology would announce for it. ## Computed role versus the markup The distinction the question turns on is which of two things you are reading. - `getDomAttribute("role")` returns the literal `role` token that the markup declared, or `null` when the markup declared none. It is a string comparison against the template. - `getAriaRole()` returns what the browser computed, which combines the element's implicit role with any `role` attribute the browser accepted. | element on the dispatch board | `getDomAttribute("role")` | `getAriaRole()` | |---|---|---| | `<button id="optimise-route">` | `null` | `button` | | `<div role="button" class="stop-action">` | `button` | `button` | | `<nav class="route-steps">` | `null` | `navigation` | | `<input type="checkbox" class="delivered">` | `null` | `checkbox` | The first and last rows are the interesting ones: the markup read reports nothing, and the computed read reports the role a user of assistive technology actually gets. ## Where the value comes from Both calls are backed by dedicated W3C WebDriver commands rather than by injected script: - `getAriaRole()` issues `GET /session/{session id}/element/{element id}/computedrole`, whose remote-end steps are "compute the WAI-ARIA role of element". - `getAccessibleName()` issues `GET /session/{session id}/element/{element id}/computedlabel`, defined as the result of an accessible-name computation for the element. The computation itself belongs to the browser, not to Selenium. Two consequences follow: the values are as good as the browser's accessibility engine, and a role token the browser did not accept does not automatically become the computed role. On the interface, `getAriaRole()` and `getAccessibleName()` are `default` methods on `WebElement` that throw `UnsupportedOperationException`; `RemoteWebElement` implements them, so every driver the Java client ships against supports them. In the Python client the same two reads are properties, spelled `aria_role` and `accessible_name`. ## Where it earns its place - **Reading a widget that is not what its tag says.** A route planner's "Optimise" control built from a `<div>` with `role="button"` and a keyboard handler reads as `button` here, so a check does not have to know which of the two markup shapes the team used this quarter. - **Reading what a screen reader would announce.** `getAccessibleName()` collapses the several ways a control can be labelled into the one string that is actually exposed, which no single attribute read reproduces. - **Catching a regression in the exposed semantics.** A refactor that drops `role="button"` from the stop-action control changes the computed role even when the styling, the text and the click handler are untouched. ## Reading the pair together A single element answers three different questions depending on which read you use, and saying which is which is most of what an interviewer is checking: - `getTagName()` gives the qualified tag name - `div`, `button`, `input` - and nothing about semantics. - `getAriaRole()` gives the role the element exposes, whether that came from the tag or from a `role` attribute. - `getAccessibleName()` gives the name the element exposes, whichever labelling mechanism produced it. On a dispatch board built from `<div role="button" class="stop-action">Re-sequence</div>`, those three reads return `div`, `button` and `Re-sequence` respectively. Each is a separate command and a separate round trip, so read the one you actually need rather than all three per row. ## Its limits - It is one more round trip per element, like every other read on this interface. - The value reflects the browser's own computation, so a role can legitimately differ between browsers on unusual markup, and it is not a substitute for a real accessibility audit of the page. - It answers what role the element exposes, not whether the element is visible, enabled or interactive — those remain `isDisplayed()`, `isEnabled()` and `isSelected()`. - There is no matching *locator* here; this is a read on an element you have already found. ## The short version for an interview `getAriaRole()` gives the role the browser computed, implicit roles included; `getDomAttribute("role")` gives the token the markup declared, `null` included. Reach for the computed read when you care what the control *is* to a user, and for the markup read when you care what the template wrote.
- What does getAccessibleName() return, and where does the value come from?It returns the accessible name the browser computed for the element - the string assistive technology would announce - via the `GET .../element/{id}/computedlabel` command. The computation is the browser's accessible-name algorithm, which collapses the several ways a control can be labelled into one string. No single attribute read reproduces it, which is the point: you get the exposed name rather than whichever attribute the template happened to use.
- Can getAriaRole() and getDomAttribute("role") ever return the same thing?Yes, and routinely: on a `<div role="button">` both return `button`, because the browser accepted the declared token as the computed role. They diverge when the markup declares no role - the computed read still returns the tag's implicit role while the markup read returns `null` - and when the browser did not accept the token the template wrote.
saying these in an interview costs you the question
- Says it just returns the role attribute from the markup
- Expects null for an element with no role attribute
- Thinks Selenium computes the role itself rather than the browser
- Treats a computed role as proof the page is accessible
- Confuses the computed role with the accessible name