question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

ByText finds children of hidden elements

See original GitHub issue
  • @testing-library/react version: 11.1.0
  • Testing Framework and version: I am using the built-in testing tools that come with create-react-app @testing-library/jest-dom: 5.11.4 @testing-library/user-event: 12.1.10 react-scripts: 4.0.3 jest: 26.6.0 (hoisted from react-scripts)
  • DOM Environment: jsdom: 16.4.0

Relevant code or config:

Consider this collapsible element with aria-hidden attribute that displays children props

<div
  aria-hidden={isCollapsed}
  className={isCollapsed ? "hide" : "show"}
>
  {children}
</div>

This assertion fails

expect(screen.queryByText("children")).toBeNull();

What you did:

When using screen.queryByText("children") I expected not to find hidden elements that specify aria-hidden={isCollapsed} attribute. However, when running the test I could see that the element was found.

What happened:

I got the following failed test:

  ● collapses and expands children

    expect(received).toBeNull()

    Received: <div aria-hidden="true" class="hide">children</div>

       5 | test('collapses and expands children', () => {
       6 |   render(<Collapsible>children</Collapsible>)
    >  7 |   expect(screen.queryByText("children")).toBeNull();
         |                                          ^
       8 |
       9 |   userEvent.click(screen.getByRole("button", { name: "Expand" }));
      10 |   expect(screen.getByText("children")).toBeInTheDocument();

      at Object.<anonymous> (src/__tests__/index.test.js:7:42)

image

Reproduction:

I reproduced this issue in this repo: https://github.com/mancristiana/dom-testing-library-template

Problem description:

Since the findByRole query supports this scenario, I expected this would be true for other queries. The current behavior is a problem because it does not reflect the way a user would interact with our application. In this concrete example, a hidden element would not appear for the user, whereas our test finds it in the dom tree.

Suggested solution:

Seeing how this behavior is supported for ByRole queries I suggest implementing something similar for ByText query.

Issue Analytics

  • State:closed
  • Created 2 years ago
  • Reactions:5
  • Comments:6 (4 by maintainers)

github_iconTop GitHub Comments

2reactions
mancristianacommented, Jun 30, 2021

I just don’t see why you’d want to use ByText with a11y consideration if you already have ByRole. The only concern is with teachability here.

It is not always possible to use the byRole. Consider this scenario where we have two matching paragraphs in the document containing ‘TEXT’.

<p class="visuallyHidden">
  TEXT
</p>
<p aria-hidden="true">
  TEXT
</p>

The first one with class="visuallyHidden" might inside a section with aria-live polite optimized for screen readers, whereas the other one with aria-hidden="true" appears visually, but is hidden from screen readers.

I would expect that expect(screen.getByText('TEXT')).toBeInTheDocument(); finds only one paragraph.

1reaction
eps1loncommented, Jun 3, 2021

Thanks for the feedback but we’re not going to implement this.

ByRole already does what you want and has specified behavior. Just considering aria-hidden in ByText is just fragmenting how “a11y tree inclusion” is computed in this library and causes surprising behavior. Considering a11y tree inclusion just like ByRole does comes with perf drawbacks outlined in https://github.com/testing-library/dom-testing-library/issues/929#issuecomment-817086144.

Before, people would need to know whether a query considers a11y tree inclusion or not. Now they would also need to know how a11y tree inclusion is computed depending on the query.

Read more comments on GitHub >

github_iconTop Results From Across the Web

About Queries | Testing Library
To find only elements that are children of a specific element, you can use within . If necessary, there are also a few...
Read more >
parent hidden but children still visible (I don't want them visible)!
I have already tried placing the child to be cloned inside the parent DIV before running the duplicating script... it makes no difference....
Read more >
Queries | React Native Testing Library - Open Source
If you need to find more than one element, then use findAllBy . ... All queries take at least the hidden option as...
Read more >
Selectors - WebdriverIO
The WebDriver Protocol provides several selector strategies to query an element. WebdriverIO simplifies them to keep selecting elements simple.
Read more >
filter | Cypress Documentation
Get the DOM elements that match a specific selector. ... .filter() yields the new DOM element(s) it found. .filter() is a query, ......
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found