reactjs - 使用 try/catch 测试 useEffect 钩子
问题描述
我需要catch
在获取数据请求拒绝时进行测试,但我不明白为什么没有捕获到错误并且我收到了这个错误:UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 2)
我有这样的情况:
export const Container = ({fetchFirstAsset, fetchSecondAsset}) => {
const [status, setStatus] = useState(null);
async function fetchAssets() {
setStatus(IN_PROGRESS);
try {
await fetchFirstAsset();
await fetchSecondAsset()
setStatus(SUCCESS);
} catch {
setStatus(FAILURE);
}
}
useEffect(() => {
fetchAssets();
}, []);
....
};
并像这样测试:
import {mount} from 'enzyme';
import {act} from 'react-dom/test-utils';
const fetchFirstAsset = jest.fn();
const fetchSecondAsset = jest.fn();
it('should render without errors', async () => {
fetchFirstAsset.mockReturnValueOnce(Promise.resolve());
fetchSecondAsset.mockReturnValueOnce(Promise.reject());
let component;
await act(async () => {
component = mount(
<Container
fetchFirstAsset={fetchFirstAsset}
fetchSecondAsset={fetchSecondAsset}
/>
);
});
expect(fetchSomething).toHaveBeenCalled();
});
如果我在fetchSomething
使用 evertyhing 解决时Promise.resolve()
测试用例工作正常并且测试是正确的,但是当我尝试Promise.reject()
测试用例时,catch
则不会捕获此错误并且我有unhandled promise rejection
. (为什么代码看起来像这样:在应用程序的其他地方,我使用 redux 处理状态更改,因此对 catch 的测试很容易,但在一个地方我需要为组件获取 3 个不同的资产,我决定使用useState
因为从 redux 中提取 3 种不同的状态并将其组合起来会很丑陋,useState
我认为更干净)
提前感谢您的帮助!:)
解决方案
我遇到了同样的问题,即在 useEffect() 中使用 try/catch 子句时不起作用。我做了一些搜索,看来这是一个潜在的错误,请查看:
https://github.com/testing-library/react-hooks-testing-library/issues/305
也就是说,我能够解决以下问题:
失败示例:
useEffect(() => {
try {
invokeMyAsyncFunction();
setStatus(SUCCESS);
} catch (e) {
setStatus(FAILURE); // <== will not be invoked on exception!!
}
}
成功案例:
useEffect(() => {
invokeMyAsyncFunction()
.then((response:any) => {
setStatus(SUCCESS);
})
.catch((e) => {
setStatus(FAILURE); // <== this **WILL** be invoked on exception
});
}
推荐阅读
- javascript - 单击新 div 时禁用其他 div 的样式
- database - MEAN 堆栈:如何在 mongoDB 中存储用户凭据
- salesforce - Salesforce 公式:营业时间公式不适用于营业时间以外的开始时间和营业时间内的结束时间
- python - 仅当子字符串出现一次时,正则表达式匹配
- webpack - Webpack per-entry 模块解析别名规则
- android - 执行通知操作时自动关闭 Android 9 应用上的通知
- java - 如何序列化和反序列化哈希表?
- python - 如何在 Keras 中使用 LSTM 添加 Conv2D 层?
- ag-grid - aggrid:如何在侧边栏过滤器工具面板中设置 ag-virtual-list-item 的行高?
- excel - 我的 If 函数不会被考虑在内