Skip to content

False positive on Splide li's - "aria role should be appropriate for the element" #4910

Open

Description

@mark-c-woodard

Product

axe Extension

Product Version

4.116.1

Latest Version

  • I have tested the issue with the latest version of the product

Issue Description

The Axe extension is flagging the <li> in something like <ul role="presentation"><li role="tabpanel"></li></ul> with "aria role should be appropriate for the element"
I'm seeing this issue in various sliders that use the Splide library.

I believe that the <li> should be allowed to have a tabpanel role if the parent <ul> does not have the list role according to https://www.w3.org/TR/html-aria/#docconformance.
Please correct me if I'm reading that wrong though.

How to Reproduce

You can reproduce the issue on most any slider using Splide with the pagination dots, such as this demo on their website
https://splidejs.com/guides/themes/

You can just run the extension on a page with <ul role="presentation"><li role="tabpanel"></li></ul> and the error triggers as well.

I also did a quick recording showing the issue: https://www.loom.com/share/55b5278545424d4b86f0060ec3751c32?sid=bdccc6e6-e3fd-4749-aa25-7c89624ff092

Activity

  1. WilcoFiers commented on Oct 20, 2025

    @WilcoFiers
    Contributor

    @mark-c-woodard Thank you for reporting. I agree this is a false positive. Axe-core is working off an older version of ARIA in HTML here it seems. The current one has this to say about li roles:

    No role other than listitem, which is NOT RECOMMENDED, if the parent list element has an implicit or explicit list role.

    Otherwise, any role if the parent list element does not expose an implicit or explicit list role.

    Note
    See ul, ol, or menu for allowed roles for list elements.

    In the example you shared the parent is set to presentation, so any role would be allowed.

  2. added
    fixBug fixes
    rulesIssue or false result from an axe-core rule
    and removed
    extensionAxe Firefox or Chrome extension issues
    ungroomedTicket needs a maintainer to prioritize and label
    on Oct 20, 2025
  3. Lollo176ITA commented on Aug 13, 2026

    @Lollo176ITA

    Confirming this on a public-sector design system, in case a real-world case helps prioritise.

    Setup

    • axe-core 4.13.0, via @axe-core/puppeteer
    • Bootstrap Italia 2.18.3, the design system used for Italian public administration websites
    • Splide 4.1.4, declared by Bootstrap Italia as @splidejs/splide: ^4.1.4
    • No patching or overriding of Splide's ARIA roles

    A public example is available in the Bootstrap Italia carousel documentation, where the carousel component is implemented using Splide.

    What is reported

    aria-allowed-role is reported on every carousel slide:

    <ul class="splide__list" role="presentation">
      <li class="splide__slide" role="tabpanel" id="splide01-slide01" tabindex="-1">…</li>
    </ul>

    Where the roles come from

    These roles are not present in the design system's authored markup. Splide adds them at runtime:

    • components/Elements/Elements.ts sets role="presentation" on ul.splide__list
    • components/Slides/Slide.ts sets role="tabpanel" on li.splide__slide when pagination is enabled
    • Without pagination, the slide role becomes group

    This appears to be the same underlying issue described in Splidejs/splide#825.

    According to the current HTML-ARIA conformance rules, an li is restricted to list-item-related roles when its parent exposes an implicit or explicit list role. Otherwise, any role is allowed. Since Splide changes the parent list's role to presentation, tabpanel should be permitted on the child li.

    The current lib/standards/html-elms.js implementation appears to model li with a flat allowedRoles array and does not take the parent element's exposed role into account.

    Why authors cannot work around it cleanly

    Disabling pagination does not resolve the finding: the slide role changes from tabpanel to group, which is also absent from the current allowed-role list for li.

    The only structural workaround available to authors is to use div elements instead of ul/li:

    <div class="splide__list">
      <div class="splide__slide">…</div>
    </div>

    This works because Splide resolves slides by the .splide__slide class rather than by tag name, and the relevant Bootstrap Italia styles use class selectors rather than relying on ul/li selectors.

    However, this requires downstream users to diverge from the design system's documented markup solely to avoid an automated false positive. Runtime monkey-patching after Splide's mounted event would be another workaround, but it is also not a reasonable requirement for every consumer.

    Impact

    Bootstrap Italia is used by Italian public administration websites, many of which include automated accessibility checks in their development or audit processes. As a result, this finding can appear on every page containing a carousel, and each team has to independently determine that it is a false positive rather than an actual authoring error.

    This is especially costly because the finding is attached to every slide, creating repeated noise in audit results and making it harder to identify genuine accessibility issues.

    Happy to provide a reduced test case, a public URL, or a patch if useful.

  4. added this to the Axe-core next milestone on Oct 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    best practicefixBug fixeshighHigh priorityrulesIssue or false result from an axe-core rule

    Type

    No type

    Projects

    No projects

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions