useLocation 不能被 jest.fn() 模拟(而 useHistory 可以)
useLocation can't be mocked with jest.fn() (while useHistory can be)
我正在尝试使用 useHistory
和 useLocation
为 React 组件编写测试,如下所示:
import { useHistory, useLocation } from 'react-router-dom';
export function MyComponent() {
let location = useLocation();
let history = useHistory();
function changeUrl(param) {
// some logic here
if(foo) {
history.push(location.pathname);
} else {
history.push(param)
}
}
return (<div>{/* actual elements here */}</div>)
}
这是测试文件:
import { render } from "@testing-library/react";
jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
useLocation: jest.fn().mockImplementation(() => ({ pathname: 'a' })),
useHistory: jest.fn().mockImplementation(() => ({ push: () => { } })),
}));
it('should do xxx', () => {
render(<MyComponent/>);
});
这导致
Error: Uncaught [TypeError: Cannot read property 'pathname' of undefined]
错误源自location.pathname
。同时,useHistory
不会抛出任何错误。
有人看到哪里出了问题吗?任何建议将不胜感激。
PS
如果我像下面这样在 it
中使用 mockImplementation
,则不会发生错误。
jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
useHistory: jest.fn().mockImplementation(() => ({ push: () => { } })),
}));
const { useLocation } = require('react-router-dom');
it('should do xxx', () => {
useLocation.mockImplementation(() => { pathname: 'a' });
render(<MyComponent/>);
});
我不明白为什么会这样...
不要单独模拟每个钩子,而是使用 <Memory router>
render(
<MemoryRouter initial entries={['/a']}>
<My component/>
</MemoryRouter>
)
React Router 文档中的更多示例,第 Testing 部分。模拟单个钩子不太灵活。
我正在尝试使用 useHistory
和 useLocation
为 React 组件编写测试,如下所示:
import { useHistory, useLocation } from 'react-router-dom';
export function MyComponent() {
let location = useLocation();
let history = useHistory();
function changeUrl(param) {
// some logic here
if(foo) {
history.push(location.pathname);
} else {
history.push(param)
}
}
return (<div>{/* actual elements here */}</div>)
}
这是测试文件:
import { render } from "@testing-library/react";
jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
useLocation: jest.fn().mockImplementation(() => ({ pathname: 'a' })),
useHistory: jest.fn().mockImplementation(() => ({ push: () => { } })),
}));
it('should do xxx', () => {
render(<MyComponent/>);
});
这导致
Error: Uncaught [TypeError: Cannot read property 'pathname' of undefined]
错误源自location.pathname
。同时,useHistory
不会抛出任何错误。
有人看到哪里出了问题吗?任何建议将不胜感激。
PS
如果我像下面这样在 it
中使用 mockImplementation
,则不会发生错误。
jest.mock('react-router-dom', () => ({
...jest.requireActual('react-router-dom'),
useHistory: jest.fn().mockImplementation(() => ({ push: () => { } })),
}));
const { useLocation } = require('react-router-dom');
it('should do xxx', () => {
useLocation.mockImplementation(() => { pathname: 'a' });
render(<MyComponent/>);
});
我不明白为什么会这样...
不要单独模拟每个钩子,而是使用 <Memory router>
render(
<MemoryRouter initial entries={['/a']}>
<My component/>
</MemoryRouter>
)
React Router 文档中的更多示例,第 Testing 部分。模拟单个钩子不太灵活。