duboloms
@duboloms
Люблю есть дубы с кетчупом. Веб-разработчик.

Будет ли react-router-dom перерисовывать страницу, если я передам useState значение?

Привет.
У меня есть свой хук, называется auth. Из него я получаю token, ready и другие параметры (но токен более важен в вопросе)
Есть страница авторизации, по jwt токену.
Есть также роуты, которые принимают параметр isAuth, если он true (truthy), то react router dom отрисовывает страницу авторизованного пользователя (ему доступны основные функции приложения), если token является false (falsy) то тогда отображается форма регистрации/входа в приложение
Когда пользователь входит в аккаунт (есть форма, в которой нажимает кнопку), в token записывается сгенерированный токен (он сохраняется в localstorage) но роуты не перерисовываются! Хотя token обернут в useState(). Он должен редиректить на /home, и отрисовать HomePage. Однкако, этого не происходит.
(После обновления страницы, все работает)

Вот кусочек из App.js:
import React, {useState, useEffect} from "react";
import {BrowserRouter as Router} from "react-router-dom";
// routes
import {useRoutes} from "./routes";
// hooks
import {useAuth} from "./hooks/auth.hook";
// context
import {AuthContext} from "./context/auth.context";
// components
import {Loader} from "./components/Loader";

function App() {
  const {login, logout, token, userId, ready} = useAuth();
  const isAuth = !!token; // "!!" - прикладываю к boolean
  const routes = useRoutes(isAuth); // token обернут в useState, но редиректа после авторизации нет
  ...


Вот auth.hook.js:
import {useState, useCallback, useEffect} from "react";

const storageName = "user";

export const useAuth = () => {
  const [token, setToken] = useState(null); // как и говорил, он обернут в useState
  const [userId, setUserId] = useState(null);
  const [ready, setReady] = useState(false);

  const login = useCallback((jwtToken, id) => {
    setToken(jwtToken);
    setUserId(id);

    localStorage.setItem(storageName, JSON.stringify({
      token: jwtToken, userId: id
    }));
  }, []);

  const logout = useCallback(() => {
    setToken(null);
    setUserId(null);

    localStorage.removeItem(storageName);
  }, []);

  useEffect(() => {
    const user = JSON.parse(localStorage.getItem(storageName));

    if(user && user.token){
      login(user.token, user.userId);
    }
    setReady(true);
  }, [login]);

  return {login, logout, token, userId, ready}
}


Что делать?
  • Вопрос задан
  • 333 просмотра
Решения вопроса 1
duboloms
@duboloms Автор вопроса
Люблю есть дубы с кетчупом. Веб-разработчик.
Вообщем, нашел ответ, у меня все из хука useAuth передавалось в контекст реакта, но в AuthPage (странице авторизации) у меня использовался напрямую useAuth хук, а не функции из контекста...

Если проще говорить, то в AuthPage, я заменил это:
const {login} = useAuth();
На это:
const {login} = useContext(AuthContext);
Ответ написан
Комментировать
Пригласить эксперта
Ответы на вопрос 2
@AleksRap
Во-первых. Логику с авторизацией нет смысла выносить в хук, т.к она используется один раз. Пользовательские хуки нужны для переиспользования логики с участием встроенных хуков реакта.
Во-вторых, не храните токен в localStorage, храните его в памяти приложения
В-третьих крайне рекомендую начать использовать редакс. В нем гораздо удобнее хранить подобное состояние

По сути вопроса - элементарно проверьте меняется ли состояние isAuth обычным console.log. Если меняется - проблема в вашем хуке useRoutes
Ответ написан
@historydev Куратор тега JavaScript
Острая аллергия на анимешников
С ответом выше согласен, я имею на каждый компонент состояние при авторизации и всё)
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы