отправка недоступна из useContext

у меня простой магазин

import React, { createContext, useReducer } from "react";
import Reducer from "./UserReducer";

const initialState = {
    user: {},
    error: null
};

const Store = ({ children }) => {
    const [state, dispatch] = useReducer(Reducer, initialState);
    return (
        <Context.Provider value={[state, dispatch]}>
            {children}
        </Context.Provider>
    );
};

export const Context = createContext(initialState);
export default Store;

Я обернул им свое приложение, как

<Store>
    <ThemeProvider theme={Theme}>
        <CssBaseline />
        <Navbar />
        <Wrapper>
            <Profile />
        </Wrapper>
    </ThemeProvider>{" "}
</Store>

Также есть дополнительная настройка, где мои страницы аутентификации расположены в отдельной оболочке, поэтому я также обернул ее хранилищем.

вот код для этой оболочки (лишнее удалено).

import Store from "../../../context/Store";
export default function Wrapper({ children }) {
    const classes = useStyles();
    return (
        <Store>
           //different dumb containers opening
                {children}
          //different dumb containers closing
        </Store>
    );
}

Теперь, когда я пытаюсь получить доступ к контексту в дочернем компоненте, например

import React, { useContext } from "react";
import { Context } from "../../../context/Store";
import { SET_USER } from "../../../context/UserTypes";

function SignUp(props) {
    const [state, setState] = React.useState({ ...initialState });

    const [userData, dispatch] = useContext(Context);
    console.log(userData, dispatch, "check");
// rest of component

я получаю следующую ошибку

TypeError: undefined is not a function

Я попытался зарегистрировать результат useContext, не разрушая его, но все, что у него было, было глобальным состоянием, но без функции отправки с ним.

Версия Reactjs = 17.0.1

Обновление: отправка доступна снаружи с помощью Authenticator HOC, но не внутри него, поэтому это может быть проблемой.

Открыл выпуск по усиленному репо.

Невозможно получить доступ к отправке из useContext из компонентов, заключенных в Authenticator


person Muhammad Faizan Ul Haq    schedule 30.12.2020    source источник


Ответы (1)


Я вижу несколько вещей, которые могут быть потенциальными проблемами.

Основная проблема - это ценность вашего Context. Когда вы создаете контекст, его значением является состояние (createContext(initialState)). Но когда вы передаете value в Context.Provider, вы даете ему массив, который содержит как состояние, так и функцию отправки (value={[state, dispatch]}). Вы должны быть последовательны в отношении ценности, содержащейся в контексте. Это объект состояния или кортеж?

Ошибка, которую вы описываете, похоже на то, что произойдет, если доступ к Context будет осуществляться за пределами Provider. Он вернет исходное значение контекста, которое является просто состоянием, а не кортежем [state, dispatch].

Вам нужно изменить начальное значение на то, что соответствует ожидаемому значению.

const Context = createContext([
  initialState, // state
  () => console.error("Cannot dispatch because Context was used outside of a provider") // dispatch
]);

Но вам также необходимо выяснить, почему useContext получает значение по умолчанию вместо значения из Provider. Я не уверен, что следующие две проблемы исправят это или нет.

Похоже, что компонент Profile находится внутри двух разных Store провайдеров. Один, который находится вне всего, и один, который находится внутри компонента Wrapper. У них будет два отдельных экземпляра состояния. Когда есть два поставщика для одного и того же контекста, React использует внутренний. Таким образом, любые действия, которые вы отправляете из Profile, не будут обновлять внешнюю версию Store.

Вы создаете Context переменную после использования ее в своем Store компоненте. Вы должны изменить порядок.

person Linda Paiste    schedule 24.01.2021