[英]How to mock dispatch with jest.fn()
例如,我想知道发送了什么以及参数。 动作创建者是异步的,但我不关心它的实现,我只想知道组件是否使用正确的参数调度了正确的动作创建者。 我试过这种方法:
store.dispatch = jest.fn()
但我无法获得任何有用的信息:
我试图通过这种方式解决问题:
expect(store.dispatch.mock.calls[0].toString()).toBe(requestArticles().toString())
但我不知道这个论点,我敢肯定,有更好的方法来做到这一点。 另外值得注意的是,我使用的是 react-testing-library,所以我不能使用 Enzyme 的wrapper.instance().props
。
您可以模拟操作文件并检查该操作是否已被调用。
例如,可以说foo.action.js
是具有正在调度的操作的文件。
在导入组件之前的测试文件的开头,您可以将文件模拟为:
const yourActionMock = jest.fn();
jest.mock('<Path to the action file>/foo.action.js', () => ({
yourAction: yourActionMock
}));
现在您可以测试名为的操作: expect(yourActionMock).toHaveBeenCalledWith(<args>)
如果您使用的是 react-redux 挂钩,您可以这样做:
import * as reactRedux from 'react-redux';
const mockDispatch = jest.fn();
const mockUseDispatch = jest.spyOn(reactRedux, 'useDispatch');
然后像往常一样在mockDispatch
上做出断言。
这是一个对我有用的例子(2022):
(导航栏.test.js)
import store from "../../store/redux-store";
import { useDispatch, useSelector } from "react-redux";
import { Provider } from "react-redux";
import configureStore from "redux-mock-store";
import { render, screen, cleanup, waitFor } from "@testing-library/react";
import userEvent from "@testing-library/user-event";
import Navbar from "../navbar/Navbar";
describe("Navbar", () => {
beforeEach(() => {
// ! WE MAKE SURE THE MOCKS ARE CLEARED BEFORE EACH TEST CASE
useSelectorMock.mockClear();
useDispatchMock.mockClear();
});
afterAll(() => {
cleanup();
});
// ! SETUP THE SPY ON USESELECTOR / USE DISPATCH
// ! WE DO THIS TO BE ABLE TO CHECK IF THE DISPATCH MOCK GOT CALLED AND HOW MANY TIMES
const reactRedux = { useDispatch, useSelector }
const useDispatchMock = jest.spyOn(reactRedux, "useDispatch");
const useSelectorMock = jest.spyOn(reactRedux, "useSelector");
[...]
test("cliking the sign-out button should sign out user", async () => {
const mockStore = configureStore();
const initialState = {
auth: {
isAuthModalOpen: false,
user: { id: 1, email: "test@test.com" },
notification: null,
isLoggedIn: true,
token: "ABC123",
},
};
let updatedStore = mockStore(initialState);
const mockDispatch = jest.fn();
useDispatchMock.mockReturnValue(mockDispatch);
updatedStore.dispatch = mockDispatch;
// ? HERE THE INITIAL CONTENT OF THE MOCK
// console.log(updatedStore.dispatch.mock);
render(<Provider store={updatedStore}><Navbar /></Provider>);
const signOutBtn = screen.getByTestId("button-sign-out");
expect(signOutBtn).toBeInTheDocument();
expect(updatedStore.dispatch).not.toHaveBeenCalled();
userEvent.click(signOutBtn);
// ? HERE THE CONTENT OF THE MOCK CHANGED
// console.log(updatedStore.dispatch.mock);
expect(updatedStore.dispatch).toHaveBeenCalledTimes(1);
expect(updatedStore.dispatch.mock.lastCall[0].type).toMatch("destroySession");
screen.debug()
console.log(updatedStore.getActions());
});
注意从 react-redux 导入“useDispatch”的方式的不同。 另外,请注意“mockDispatch”附加到“updatedStore.dispatch”的方式。
这两个变化使它对我有用。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.