admin管理员组文章数量:1318976
I have a function that calls useSelector multiple times upon rendering. In mocking the selector I used:
jest.spyOn(Redux, 'useSelector').mockReturnValueOnce(data).mockReturnValueOnce(moreData);
This changes the order of how hooks are called in my ponent. I have also tried creating a mock store and sending that into rendered ponent in the test as such:
const state = { userGuid: 'testGuid', user };
const store = mockStore(state);
jest.spyOn(Redux, 'useSelector').mockImplementation(() => store.getState());
const { getByTestId } = wrappedRender(ProfileScreen, mockProps, { store });
But this wraps the data in an extra object which my ponent cannot de-structure.
As of now I cannot find any other way to mock the return values of multiple useSelector calls without changing the order of hooks called. Any help is appreciated.
I have a function that calls useSelector multiple times upon rendering. In mocking the selector I used:
jest.spyOn(Redux, 'useSelector').mockReturnValueOnce(data).mockReturnValueOnce(moreData);
This changes the order of how hooks are called in my ponent. I have also tried creating a mock store and sending that into rendered ponent in the test as such:
const state = { userGuid: 'testGuid', user };
const store = mockStore(state);
jest.spyOn(Redux, 'useSelector').mockImplementation(() => store.getState());
const { getByTestId } = wrappedRender(ProfileScreen, mockProps, { store });
But this wraps the data in an extra object which my ponent cannot de-structure.
As of now I cannot find any other way to mock the return values of multiple useSelector calls without changing the order of hooks called. Any help is appreciated.
Share Improve this question edited Oct 2, 2020 at 16:50 Drew Reese 204k18 gold badges240 silver badges271 bronze badges asked Oct 2, 2020 at 16:32 JacobJacob 3013 silver badges13 bronze badges2 Answers
Reset to default 6Relying on mockReturnValueOnce
calls multiple times is a no-go as the order might change. The code below will just return the stubbed state no matter how many times useSelector
is being called.
import * as redux from 'react-redux'
const user = {
id: 1,
name: 'User',
}
const state = { user }
jest
.spyOn(redux, 'useSelector')
.mockImplementation((callback) => callback(state))
you shouldn't mock useSelector and useDispatch as eplained in the redux docs here: https://redux.js/usage/writing-tests… but you could control the intialstate pased in to store in your test or dispatch action in your test which should be more desirable… and this is how i implemented it following the docs.
in store/store.js i created a function that returns a configure store function so i can pass in an initial state for the store
import { configureStore, bineReducers } from "@reduxjs/toolkit";
import { reducer } from "./yourSlice";
import { reducerTwo } from "./anotherSlice";
const rootReducer = bineReducers({
authState: reducer,
mode: reducerTwo
});
export default function setUpStore(preloadedState) {
return configureStore({ reducer: rootReducer, preloadedState });
}
in utils/RTKOveride.js
import { render } from "@testing-library/react";
import { Provider } from "react-redux";
import setUpStore from "store/store";
function renderWithWrapers(ui,
{
preloadedState = {},
store = setUpStore(preloadedState),
...options
} = {},
) {
function Wrapper({ children }) {
return (
<Provider store={store}>
{children}
</Provider>
);
}
return { store, ...render(ui, { wrapper: Wrapper, ...options }) };
}
export * from "@testing-library/react";
export { renderWithWrapers as render };
i overide the render function from RTK, wrapped my ponents that will be passed via the props.children in the provider ponent so ponents using useSelector and useDispatch still function properly. even if you do not pass in a store or preloadedState(initialState) the code wont break as a store is created everytime the renderedWithWrapper is called
NOTE: the official react testing tookit explains how you could overide the render method and pass in additional options
then in your test/Component.test.js
import { render, screen } from "utils/RtkOveride";
import SomeComponent from "../Component";
test("some foo test", () => {
render(
<SomeComponent />
, { preloadedState: { authState: { state: true, refresh: "", access: "" } } }
);
const inputBar = screen.queryByText("foo", { exact: false });
expect(inputBar).toBeInTheDocument();
});
So you could pass in an initialState to change the default Slice InitialState or follow the other way the redux docs detailed... Hopes this helps.
本文标签: javascriptHow to properly mock useSelector hook to return correct values while testingStack Overflow
版权声明:本文标题:javascript - How to properly mock useSelector hook to return correct values while testing? - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1742056418a2418321.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论