Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

having ref in react component causes renderIntoDocument DOM to become empty #95

Closed
henrickyau opened this issue May 25, 2018 · 5 comments

Comments

@henrickyau
Copy link

  • react-testing-library version: 3.1.0
  • react version: 16.3.2
  • node version: 8.9.1
  • npm (or yarn) version: 5.5.1

Relevant code or config:

describe("WebhookSender Fetch", () => {

    beforeEach(() => {
        Rendered = renderIntoDocument(componentMarkup);
    });

    afterEach(() => {
        cleanup();
        fetch.resetMocks();
    });

    it("should show render results", async (done) => {

        fetch.mockReject(fetchRejectMsg);
        const sendBtnNode = Rendered.getByText('Send');
        fireEvent(sendBtnNode, new MouseEvent('click', {
            bubbles: true, 
            cancelable: true,
          }));

        await wait(() => Rendered.getByText(fetchRejectMsg));
        expect(Rendered.getByText(fetchRejectMsg, {exact: false})).toBeInTheDOM();
        done();
    });

});

What you did:

The test is successful if I comment out the following div with ref, in my react component being tested:

<div ref={(bottom) => { this.fetchBottom = bottom; }}>
    <p>&nbsp;</p>
</div>

What happened:

When the div with ref is there, the test fails and the console shows

console.error node_modules/react-dom/cjs/react-dom.development.js:9643
  The above error occurred in the <WebhookSender> component:
      in WebhookSender (at WebhookSender.spec.js:18)
      in MuiThemeProvider (at WebhookSender.spec.js:17)
  
  Consider adding an error boundary to your tree to customize error handling behavior.
  Visit https://fb.me/react-error-boundaries to learn more about error boundaries.
console.error node_modules/fbjs/lib/warning.js:33
  Warning: Can't call setState (or forceUpdate) on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the componentWillUnmount method.
      in WebhookSender (at WebhookSender.spec.js:18)
      in MuiThemeProvider (at WebhookSender.spec.js:17)

Reproduction:

Problem description:

I find that if I have the ref in my react component, after the button click, the DOM (look at PrettyDOM(Rendered.container)) becomes just an empty div , thus failing the subsequent getByText.

Is there known issue with having ref for such tests?

Suggested solution:

@kentcdodds
Copy link
Member

Could you please create a reproduction of this in codesandbox? That will help a lot I think. Fork this one: http://kcd.im/rtl-example

@henrickyau
Copy link
Author

I am not able to reproduce it in codesandbox, however, when running the code downloaded from codesandbox it reproduces. So it may be an issue with my environment. I wonder how codesandbox runs the test (is it in the browser?). In my local env it's run using jest with env=jsdom so maybe that's the issue?

@kentcdodds
Copy link
Member

If you share the sandbox you used I'll verify that. Maybe there really is a problem.

@henrickyau
Copy link
Author

Thanks for your patience. I finally figured it out. The problem was that scrollIntoView is not in jsdom (jsdom/jsdom#1695). I was expecting it to be there as a no-op.

The reproducer is here - https://codesandbox.io/s/8853vq24xl

Test passes on codesandbox. Download to local and run 'npm i' followed by 'npm test' will show failure.

So it seems I should explore setting up a browser test env instead of jsdom, vs mocking the functions not in jsdom. Do you recommend running rtl with some other test runners (like cypress, karma)? jest+rtl works very well for me so far but I would need such tests working.

@kentcdodds
Copy link
Member

Yes, we should probably have an example of how to test for this, even though it's not specific to react-testing-library. Most people are using Jest + jsdom so they'll probably run into this issue.

Here's a working "solution"

beforeAll(() => {
  if (!HTMLElement.prototype.scrollIntoView) {
    HTMLElement.prototype.scrollIntoView = () => {}
  }
})

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants