Skip to content

Implement proper support for aria-owns #4745

@WilcoFiers

Description

@WilcoFiers

Axe-core doesn't properly process aria-owns. Rules like aria-required-parent and aria-required-children don't account for it. Just generally, the rules don't understand that ARIA properties inherit on the accessibility tree, so the aria-hidden or aria-disabled properties should apply to owned elements, rather than to descendants. That impacts lots of things all over the place.

Axe has ignored aria-owned for a while because it wasn't supported in Safari + VO. That is no longer the case, so axe really needs to know about this. I think the way to do this would be to add an "owns" and "owner" property to the virtual DOM that axe can walk in the same way it walks the flat tree by using the parent / child props on VirtualNodes.

I've been trying to figure out how browsers handle edge cases. I've done a bunch of testing and had some surprising results. I'm mostly opening this ticket to have a place to put the results of this. For Firefox and Chrome I inspected the accessibility tree through devtools. For Safari I used VoiceOver to try and figure out the tree.

Duplicate IDs

<ul>
  <li id="bob">Bob A</li>
  <li id="bob">Bob B</li>
</ul>
<ul aria-owns="bob"></ul>

Chrome & Firefox

list, 1 item, "Bob A"
list, 1 item, "Bob B"

Safari (with VoiceOver) seems to get confused about this, Read everything just halts when it hits this list. Going through it line by line it repeats "Bob A", and skips "Bob B". Navigating in reverse order sometimes announces "Bob B", but not consistently.

Competing aria-owns attrs

<ul id="ul1"> <li aria-owns="ul3">LI 1</li> </ul>
<ul id="ul2"> <li aria-owns="ul3">LI 2</li> </ul>
<ul id="ul3"> <li>LI 3</li> </ul>

Chrome & Firefox

UL 1 owns UL 3

Safari:

UL 2 owns UL 3

Cyclical ownership

<ul>
  <li id="a" aria-owns="d">A</li>
  <li id="b" aria-owns="a">B</li>
  <li id="c" aria-owns="b">C</li>
  <li id="d" aria-owns="c">D</li>
</ul>

Chrome

D > C > B > A

Firefox & Safari

C > B > A > D

Invalid aria-owns

<ul id="foo">
  <li>foo</li>
  <li id="bar" aria-owns="foo">Bar</li>
</ul>
<ul aria-owns="bar"></ul>
<section aria-owns="foo"></section>

Bar obviously cannot own its parent. But surprisingly that doesn't prevent another element with aria-owns from adopting ul#foo. Chrome, Firefox, Safari seem consistent in this, there are two lists with one item, the first with "bar" and the second with "foo".

list > listitem > "bar"
list > listitem > "foo"

Metadata

Metadata

Assignees

No one assigned

    Labels

    fixBug fixes

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions