开玩笑:““找不到react-redux上下文值;请确保组件 Package 在< Provider>“

4ktjp1zp  于 2022-11-12  发布在  React
关注(0)|答案(2)|浏览(193)

我在尝试使用表单React组件执行简单的Jest测试时遇到此错误:

● <LoginForm /> › clicking the validate button › should display page title                              

    could not find react-redux context value; please ensure the component is wrapped in a <Provider>      

      14 |      const [inputPassword, setInputPassword] = useState("");                                   
      15 |                                                                                                
    > 16 |      const dispatch = useDispatch();

下面是组件本身:

import React, { useState, useEffect } from "react";
import { useDispatch } from "react-redux";
import { useHistory } from "react-router-dom";
import jwt_decode from "jwt-decode";
import Cookies from "js-cookie";

import post from "../../../services/request/Post";
import { setCurrentUser } from "../../../redux/action";
import "./index.scss";

const LoginForm = () => {
    const [userData, setUserData] = useState(null);
    const [inputEmail, setInputEmail] = useState("");
    const [inputPassword, setInputPassword] = useState("");

    const dispatch = useDispatch();
    const history = useHistory();

    const handleEmailChange = (e) => {
        setInputEmail(e.target.value);
    };

    const handlePasswordChange = (e) => {
        setInputPassword(e.target.value);
    };

    const handleSubmit = (e) => {
        e.preventDefault();
        setUserData({
            ...userData,
            email: inputEmail,
            password: inputPassword
        });
    };

    const handleLogin = async (data) => {
        if (data) {
            let body = {
                user: { email: data.email, password: data.password }
            };
            const response = await post("/tokens", body);
            if (response != null) {
                Cookies.set("token", response.data.token, {
                    sameSite: "strict",
                    Secure: true
                });
                const payload = {
                    type: "user",
                    id: jwt_decode(response.data.token).user_id,
                    email: userData.email,
                    username: response.data.username
                };
                dispatch(setCurrentUser(payload));
                history.push("/");
            }
        }
    };

    useEffect(() => {
        handleLogin(userData);
    }, [userData]);

    return (
        <div className="LoginForm">
            <form action="" onSubmit={handleSubmit}>
                <label htmlFor="email">Adresse email</label>
                <input
                    type="email"
                    id="email"
                    name="email"
                    value={inputEmail}
                    onChange={handleEmailChange}
                />

                <label htmlFor="password">Mot de passe</label>
                <input
                    type="password"
                    id="password"
                    name="password"
                    value={inputPassword}
                    onChange={handlePasswordChange}
                />

                <button type="submit" id="submitButton">
                    Valider
                </button>
            </form>
        </div>
    );
};

export default LoginForm;

下面是主要的.jsx组件(入口点):

ReactDOM.render(
    <React.StrictMode>
        <Provider store={store}>
            <PersistGate loading={null} persistor={persistor}>
                <App />
            </PersistGate>
        </Provider>
    </React.StrictMode>,
    document.getElementById("root")
);

可以看到,我已经将<App />组件 Package 在<Provider>
最后,下面是我编写的一个非常简单的测试:

import React from 'react';
import { render, screen } from "@testing-library/react";
// import userEvent from "@testing-library/user-event";

import LoginForm from '../components/forms/LoginForm';

describe('<LoginForm />', () => {
  describe('clicking the validate button', () => {
    beforeEach(
      render(<LoginForm />)
    );

    it("should display page title", () => {
      expect(screen.getByText("Page de connexion")).toBeInTheDocument();
      expect(screen.getByText("Adresse email")).toBeInTheDocument();
      expect(screen.getByText("Mot de passe")).toBeInTheDocument();
    })
  });
});

这是我第一次用React写测试,所以我有点困惑。我应该用一种模拟存储来测试环境吗?如果是的话,是否可以对每个被测试的组件全局地做?

2w2cym1i

2w2cym1i1#

是的,您应该使用<Provider store={store}> Package <LoginForm />
您可以设置一个可重复使用的函数,它将自动为您执行此操作:
https://redux.js.org/usage/writing-tests#components

dojqjjoe

dojqjjoe2#

在我的例子中,为了能够模拟存储和提供程序,我根据我的应用程序的redux文档实现了一个名为renderWithProviders的自定义呈现函数,该应用程序是使用Typescript、Webpack、React-Redux和Jest构建的。
参考

相关问题