按照本文blog post中介绍的Kent C Dodds的提供者模式,我有一个上下文提供者组件以及一个使用该上下文的钩子。
钩子防止在提供者之外使用它,
export function useUser() {
const { user } = useContext(UserContext) || {};
const { switchUser } = useContext(SwitchUserContext) || {};
if (!user || !switchUser) {
throw new Error('Cannot use `useUser` outside of `UserProvider`');
}
return { user, switchUser };
}
为了测试这个场景,我创建了一个TestComponent
并在其中使用useUser
钩子。
function TestComponent() {
const { user, switchUser } = useUser();
return (
<>
<p>User: {user.name}</p>
<button onClick={switchUser}>Switch user</button>
</>
);
}
我这样测试
test('should throw error when not wrapped inside `UserProvider`', () => {
const err = console.error;
console.error = jest.fn();
let actualErrorMsg;
try {
render(<TestComponent />);
} catch(e) {
actualErrorMsg = e.message;
}
const expectedErrorMsg = 'Cannot use `useUser` outside of `UserProvider`';
expect(actualErrorMsg).toEqual(expectedErrorMsg);
console.error = err;
});
我目前必须模拟console.error
,然后在测试结束时将其设置为原始值。这是可行的。但是我想让它更简单明了。有没有一个好的模式来实现它?也许是使用. toThrow()的东西?
我有一个codesandbox,上面的代码可以在UserContext.js
和UserContext.test.js
中找到。
注意:测试可以在Tests
选项卡下的codesandbox中运行。
4条答案
按热度按时间kg7wmglp1#
正如你已经提到的,有
expect().toThrow()
:)在你的例子中:
关于
console.error
:目前,设计上没有办法关闭默认错误日志。如果你想隐藏错误,你仍然需要模拟console.error
。当模拟像
console.error
这样的函数时,您希望在afterEach
回调中恢复它们,以便在测试失败时也恢复它们。hwamh0ep2#
你可以做这样的事
iqih9akk3#
它可能不是一个干净的解决方案,但它很简单,很容易弄清楚。这个例子使用了TypeScript,但没有它也能正常工作。设置类似的东西一次并在其他地方重用它也相当容易。
gmxoilav4#
对于全面覆盖和干净的控制台: