如何测试异步useEffect?
How to test async useEffect?
如何使用 react-testing-libs
测试异步 useEffect
?
我有:
// in other file
const getData = () => {
return new Promsise(resolve => setTimeout(() => resolve([1, 2, 3]), 5000));
};
const MyComponent = () => {
const [data, setData] = useState([]);
useEffect(() => {
const fetchData = async () => {
const data = await getData();
setData(data);
};
fetchData();
}, []);
return <div>{data.map(item => <span>{item}</span>)}</div>
};
如何测试这个组件?
我现在的测试:
it('MyComponent test', async () => {
await act( async () => {
render(<MyComponent/>, container);
});
expect(container.innerHTML).toMatchSnapshot();
});
但是 act,render 不会等待 useEffect()。
为什么?
请尝试以下操作:
test('My Test', async () => {
const queries = render(<MyComponent/>, container);
expect(await queries.findByText((content, element) => element.tagName.toLowerCase() === 'span')).toBeInTheDocument();
expect(container.innerHTML).toMatchSnapshot();
})
我无法测试它,所以请告诉我它是否有效。
我读了这个comment on a react-testing-library
issue and then I took a look into this piece of documentation。似乎有很多方法可以自定义此测试行为。
react-testing-library 有一个干净的解决方案。您可以等待元素出现在 DOM 中,这意味着您的异步 useEffect
运行 它的过程。
它被称为 waitFor,它将等待断言完成,然后再继续代码。您可以使用其他实用程序,例如 getByText
到 expect
it('MyComponent test', async () => {
await act( async () => {
render(<MyComponent/>, container);
});
waitFor(() => {
// I'd look for a real text here that is renderer when the data loads
expect(container.queryElement('span')).toBeDefines();
})
expect(container.innerHTML).toMatchSnapshot();
});
如何使用 react-testing-libs
测试异步 useEffect
?
我有:
// in other file
const getData = () => {
return new Promsise(resolve => setTimeout(() => resolve([1, 2, 3]), 5000));
};
const MyComponent = () => {
const [data, setData] = useState([]);
useEffect(() => {
const fetchData = async () => {
const data = await getData();
setData(data);
};
fetchData();
}, []);
return <div>{data.map(item => <span>{item}</span>)}</div>
};
如何测试这个组件?
我现在的测试:
it('MyComponent test', async () => {
await act( async () => {
render(<MyComponent/>, container);
});
expect(container.innerHTML).toMatchSnapshot();
});
但是 act,render 不会等待 useEffect()。
为什么?
请尝试以下操作:
test('My Test', async () => {
const queries = render(<MyComponent/>, container);
expect(await queries.findByText((content, element) => element.tagName.toLowerCase() === 'span')).toBeInTheDocument();
expect(container.innerHTML).toMatchSnapshot();
})
我无法测试它,所以请告诉我它是否有效。
我读了这个comment on a react-testing-library
issue and then I took a look into this piece of documentation。似乎有很多方法可以自定义此测试行为。
react-testing-library 有一个干净的解决方案。您可以等待元素出现在 DOM 中,这意味着您的异步 useEffect
运行 它的过程。
它被称为 waitFor,它将等待断言完成,然后再继续代码。您可以使用其他实用程序,例如 getByText
到 expect
it('MyComponent test', async () => {
await act( async () => {
render(<MyComponent/>, container);
});
waitFor(() => {
// I'd look for a real text here that is renderer when the data loads
expect(container.queryElement('span')).toBeDefines();
})
expect(container.innerHTML).toMatchSnapshot();
});