How to solve the "update was not wrapped in act()" warning in testing-library-react?
I'm working with a simple component that does a side effect. My test passes, but I'm getting the warning Warning: An update to Hello inside a test was not wrapped in act(...)..
I'm also don't know if waitForElement is the best way to write this test.
My component
export default function Hello() {
const [posts, setPosts] = useState([]);
useEffect(() => {
const fetchData = async () => {
const response = await axios.get('https://jsonplaceholder.typicode.com/posts');
setPosts(response.data);
}
fetchData();
}, []);
return (
<div>
<ul>
{
posts.map(
post => <li key={post.id}>{post.title}</li>
)
}
</ul>
</div>
)
}
My component test
import React from 'react';
import {render, cleanup, act } from '@testing-library/react';
import mockAxios from 'axios';
import Hello from '.';
afterEach(cleanup);
it('renders hello correctly', async () => {
mockAxios.get.mockResolvedValue({
data: [
{ id: 1, title: 'post one' },
{ id: 2, title: 'post two' },
],
});
const { asFragment } = await waitForElement(() => render(<Hello />));
expect(asFragment()).toMatchSnapshot();
});Updated answer: Please refer to @mikaelrs comment below. No need for the waitFor or waitForElement. You can just use findBy* selectors which return a promise that can be awaited. e.g await findByTestId('list'); Deprecated answer: Use waitForElement is a correct way, from the docs: Wait until the mocked get request promise resolves and the component calls setState and re-renders. waitForElement waits until the callback doesn't throw an error Here is the working example for your case: index.jsx: import React, { useState, useEffect } from 'react'; import axios from 'axios'; export default function Hello() { const [posts, setPosts] = useState([]); useEffect(() => { const fetchData = async () => { const response = await axios.get('https://jsonplaceholder.typicode.com/posts'); setPosts(response.data); }; fetchData(); }, []); return ( <div> <ul data-testid="list"> {posts.map((post) => ( <li key={post.id}>{post.title}</li> ))} </ul> </div> ); } index.test.jsx: import React from 'react'; import { render, cleanup, waitForElement } from '@testing-library/react'; import axios from 'axios'; import Hello from '.'; jest.mock('axios'); afterEach(cleanup); it('renders hello correctly', async () => { axios.get.mockResolvedValue({ data: [ { id: 1, title: 'post one' }, { id: 2, title: 'post two' }, ], }); const { getByTestId, asFragment } = render(<Hello />); const listNode = await waitForElement(() => getByTestId('list')); expect(listNode.children).toHaveLength(2); expect(asFragment()).toMatchSnapshot(); }); Unit test results with 100% coverage: PASS stackoverflow/60115885/index.test.jsx ✓ renders hello correctly (49ms) -----------|---------|----------|---------|---------|------------------- File | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s -----------|---------|----------|---------|---------|------------------- All files | 100 | 100 | 100 | 100 | index.jsx | 100 | 100 | 100 | 100 | -----------|---------|----------|---------|---------|------------------- Test Suites: 1 passed, 1 total Tests: 1 passed, 1 total Snapshots: 1 passed, 1 total Time: 4.98s index.test.jsx.snapshot: // Jest Snapshot v1 exports[`renders hello correctly 1`] = ` <DocumentFragment> <div> <ul data-testid="list" > <li> post one </li> <li> post two </li> </ul> </div> </DocumentFragment> `; source code: https://github.com/mrdulin/react-apollo-graphql-starter-kit/tree/master/stackoverflow/60115885
Get this solution programmatically \u2014 free, no authentication.
curl https://depscope.dev/api/error/ab2fda37b42a9c4dc25dfe226b4e4eea855f4973db1014dd4b1b93cc8750d73c