Dom-testing-library: waitForElement not responding to text-only updates to the markup.

Created on 15 Jul 2018  ·  4Comments  ·  Source: testing-library/dom-testing-library

  • react-testing-library version: 4.1.2
  • react version: 16.1.0
  • node version: 8.11.3
  • npm (or yarn) version: 5.6.0

Relevant code or config:

Test

test('render error message if products fail to load', async () => {
  axios.get.mockReturnValue(new Promise((resolve, reject) => reject('some error')));

  const { queryByText, getByText, debug } = renderComponent();

  expect(queryByText('Loading…')).toBeInTheDOM();
  expect(queryByText('Failed to load products')).not.toBeInTheDOM();

  await waitForElement(() => getByText('Failed to load products'));
  expect(queryByText('Failed to load products')).toBeInTheDOM();
});

React component segment

render() {
    const {
      loading,
      error,
      products,
      favourites,
      sortedBy
    } = this.props;
    if (loading) return <div data-test-id="loading-products">Loading…</div>
    if (error) return <div data-test-id="products-error">Failed to load product</div>

What you did:

Testing a component error state

What happened:

When test is executed the component remains in loading state, even when error flips to true and loading false (confirmed by console logging).

However when I wrap the text "Failed to load product" inside of an additional element such as a <span /> the test passes.

It appears to me that waitForElement is expecting a change in the markup shape rather than just text in this instance…

Reproduction:

Repository
run yarn test:reactTestingLibrary

Watch all the tests pass.
Then remove the <span /> from Products.js L39
The test should fail.

Problem description:

I'm having to change the shape of the returned JSX in order to satisfy tests.

Most helpful comment

I agree. These should be the default 👍

All 4 comments

You're right, the default mutationObserverOptions = {subtree: true, childList: true}, while the textual content monitoring seems to require a separate option, characterData: true.

For now, you can pass waitForElement(() => getByText('Failed to load products'), { mutationObserverOptions = {subtree: true, childList: true, characterData: true} }).

I'll defer to @kentcdodds the decision if we want to make it the default. I think we should, otherwise it's counter-intuitive as not every possible type of change that may affect the result of the queries is monitored. We might also want to add attributes: true to monitor attribute values.

I agree. These should be the default 👍

@rbrtsmith Would you like to submit a PR to change these default mutationObserverOptions and add tests for them?

:tada: This issue has been resolved in version 3.0.1 :tada:

The release is available on:

Your semantic-release bot :package::rocket:

Was this page helpful?
0 / 5 - 0 ratings