Skip to content

render component that set state inside of useEffect at component mount. #250

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

Closed
MuhmdRaouf opened this issue Jan 30, 2020 · 5 comments
Closed
Labels
question Further information is requested

Comments

@MuhmdRaouf
Copy link

Hey, I am trying to test a component that has useEffect and I am setting a state inside of it.

everytime tun the following test

import React from 'react';
import { render } from 'react-native-testing-library';

import { Home } from '../Home';
import { MockedProvider } from '../../core/utils/tests/mockedProvider';

describe('<Home />', () => {
  const { toJSON } = render(
    <MockedProvider>
      <Home />
    </MockedProvider>
  );

  it('should match <HomeScreen /> snapshot', () => {
    expect(toJSON()).toMatchSnapshot();
  });
});

I got the following error

  console.error node_modules/react-test-renderer/cjs/react-test-renderer.development.js:104
    Warning: An update to HomeScreen inside a test was not wrapped in act(...).
    
    When testing, code that causes React state updates should be wrapped into act(...):
    
    act(() => {
      /* fire events that update state */
    });
    /* assert on the output */
    
    This ensures that you're testing the behavior the user would see in the browser. Learn more at https://fb.me/react-wrap-tests-with-act

however, my test passes and works well.
I have searched for a solution for this and did as the error message suggested and wrapped my render method inside of act like the following

import React from 'react';
import { act, render } from 'react-native-testing-library';

import { Home } from '../Home';
import { MockedProvider } from '../../core/utils/tests/mockedProvider';

describe('<Home />', () => {
  it('should match <HomeScreen /> snapshot', async () => {
    let renderedComponent;
    await act(async () => {
      renderedComponent = render(
        <MockedProvider>
          <Home />
        </MockedProvider>
      );
    });
    expect(renderedComponent.toJSON()).toMatchSnapshot();
  });
});

and I ended up with the following error

Error: Can't access .root on unmounted test renderer

at Object.get [as root] (/Users/MuhmdRaouf/mobile-project/node_modules/react-test-renderer/cjs/react-test-renderer.development.js:15901:17)
at render (/Users/MuhmdRaouf/mobile-project/node_modules/react-native-testing-library/build/render.js:1:1517)
at _callee$ (/Users/MuhmdRaouf/mobile-project/src/screens/__tests__/Home-test.js:12:27)
at tryCatch (/Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:45:40)
at Generator.invoke [as _invoke] (/Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:271:22)
at Generator.prototype.<computed> [as next] (/Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:97:21)
  at tryCatch (/Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:45:40)
  at invoke (/Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:135:20)
  at /Users/MuhmdRaouf/mobile-project/node_modules/regenerator-runtime/runtime.js:170:11
  at tryCallTwo (/Users/MuhmdRaouf/mobile-project/node_modules/promise/lib/core.js:45:5)

is there a way to fix this problem, I know it's harmless for the time being but I wanna know the reason behind it as if I faced the same problem in the future I could be able to overcome it easily.

Thanks in Advance 😄

@MuhmdRaouf MuhmdRaouf added the question Further information is requested label Jan 30, 2020
@lucasbento
Copy link

I'm here for this as well, @thymikee is this still the same case mentioned in #200 (comment)?

@thymikee
Copy link
Member

Will try to prioritize this, thanks for the report

@thymikee
Copy link
Member

Have you seen this? https://kentcdodds.com/blog/fix-the-not-wrapped-in-act-warning

@LydGol90
Copy link

LydGol90 commented Mar 16, 2020

This works for me. I update the state inside useEffect on mount.

  it('should...', async () => {
    const { queryByType } = render(<Screen />);
    await act(async () => flushMicrotasksQueue());
    expect(...)
  });

@thymikee
Copy link
Member

Closing, as there's not much more we can do from the library perspective to deal with it. Sometimes we won't avoid using act directly, as it's stated in the mentioned blog post from my previous message.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested
Projects
None yet
Development

No branches or pull requests

4 participants