Coder Social home page Coder Social logo

Comments (4)

MatanBobi avatar MatanBobi commented on June 9, 2024

Hi @david-bezero, thanks for taking the time to open this one.
I agree that the docs section is a bit misleading but the query doesn't really apply globally.
If you'll pass a container to the render function or a baseElement, we'll use that and the query will be scoped to that.
At the moment, since you're not passing any of these, the query is bound to the body. If you'll create a new element and append it to the head, it won't be queried.
Having said that, I don't think this is a use-case that happens too often. The example you've attached (and thanks for attaching it) is really not a best practice as it has a side effect which changes the body of the component.
Do you have a better example to share?
Thanks again.

from react-testing-library.

david-bezero avatar david-bezero commented on June 9, 2024

The example you've attached is really not a best practice as it has a side effect which changes the body of the component. Do you have a better example to share?

That example matches all our existing unit tests (and the tests in every other project I've seen / worked on!), so if it's not best practice I'd be interested to know what we should be doing differently.

from react-testing-library.

MatanBobi avatar MatanBobi commented on June 9, 2024

That example matches all our existing unit tests (and the tests in every other project I've seen / worked on!), so if it's not best practice I'd be interested to know what we should be doing differently.

Do you mean that you have code inside your useEffect that adds elements to the DOM directly by creating an element? Because that's what I was referring to.

from react-testing-library.

david-bezero avatar david-bezero commented on June 9, 2024

ah; I assumed you were referring to the sentence before. The useEffect is not too far from our current scenario, but it's coming from a library we're using which internally (and temporarily) attaches an item to the DOM for rendering (with display: none, but these selectors don't omit things based on that)

A slightly more accurate representation taking that into account would be:

it('uses a consistent scope', () => {
  const MyComponent = () => {
    useEffect(() => {
      const separateElement = document.createElement('div');
      separateElement.textContent = 'hello';
      separateElement.style.display = 'none'; // not actually shown to the user
      document.body.append(separateElement);
      return () => separateElement.remove();
    }, []);

    return (
      <div>
        <div>hello</div>
      </div>
    );
  };
  const { container, getByText } = render(<MyComponent />);

  within(container).getByText('hello'); // passes
  getByText('hello'); // fails (finds 2 elements)
});

I believe the library has to attach the elements to be able to measure text (which doesn't work when detached).


Of course the other issue here is that multiple tests can interfere with each other if one fails to tear something down (causing the failure in another, "innocent", test). The most obvious scenario would be if a test fails to unmount its test component (and the developer hasn't set up an afterEach to call cleanup()), then the test passes but another may fail, and this may depend on the execution order of the tests. The rarer but still possible scenario is if a component being tested attaches an item to the DOM which it fails to clean up when unmounted, or delays removing the element due to an animation (e.g. a dialog or toast notification). Again whether this causes a failure would often depend on the execution order, making it appear "flakey").

from react-testing-library.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.