当访客进入/(家)时,如果他没有连接,我希望他被重定向到/connexion".我为此创建了私有路由,效果很好.现在,我想实现根据用户是否连接重定向用户的逻辑.

我有App.jsx条路由:

import ProtectedRoutes from './middlewares/ProtectedRoutes';

return (
    <>
      <Routes>
        <Route path="/connexion" element={<Login />} />
        <Route path="/auto-connexion" element={<AutoConnect />} />

        <Route element={<AppLayout />} >
          <Route element={<ProtectedRoutes />}>
            <Route path="/" element={<Home />} />
            <Route path="/logical-entity-selection" element={<LogicalEntitySelection />} />
            <Route path="/produits" element={<Products />} />
            <Route path="/produits/:id" element={<Product />} />
            <Route path="/actualites" element={<Articles />} />
            <Route path="/actualites/id" element={<Article />} />
            <Route path="/mes-parametres" element={<MyAccount />} />
            <Route path="/mes-outils-et-services" element={<MyToolsAndServices />} />
            <Route path='*' element={<Login />} />
          </Route>
        </Route>
      </Routes>
    </>
  );

A this ProtectedRoutes.tsx:

import { useEffect, useState } from "react"
import { Navigate, Outlet } from "react-router-dom"
import jwt_decode from "jwt-decode"
import instance from "../api/axios"

export default function ProtectedRoutes() {
    const [isLoggedIn, setIsLoggedIn] = useState(Boolean)

    const token = window.localStorage.getItem("token") || ''
    const decodedToken: any = jwt_decode(token)
    const uuid = decodedToken.uuid

    const isAuth = async () => {
        await instance.get(`/users/${uuid}`, {
            headers: {
                'Authorization': `Bearer ${token}`
            }
        }).then((res) => {
            console.log(res)
            if (res.status === 200) setIsLoggedIn(true)
            return setIsLoggedIn(false)
        })
    }

    useEffect(() => {
        isAuth()
    }, [isLoggedIn])

    return isLoggedIn ? <Outlet /> : <Navigate to={'/connexion'} />
}

问题是,对于这段代码,React渲染Login组件,因为它始终返回false,即使在我的请求后有一个状态200,并将新状态设置为true.

我如何首先提出请求,然后将新状态设置为isLoggedIn,然后决定渲染Login组件或Home组件?

我希望我说清楚了.如果没有,请毫不犹豫地问我.有什么帮助吗?

推荐答案

除了必须使其正常工作外,还需要一个加载状态,我称之为isChecking.另外,您应该更改下面的代码块,因为您正在将isLoggedIn设置为true,并将之后的代码块设置为false.

 if (res.status === 200) setIsLoggedIn(true)
 return setIsLoggedIn(false)

解决方案:

import { useEffect, useState } from "react"
import { Navigate, Outlet } from "react-router-dom"
import jwt_decode from "jwt-decode"
import instance from "../api/axios"

export default function ProtectedRoutes() {
    const [isLoggedIn, setIsLoggedIn] = useState(false)
    const [isChecking, setIsChecking] = useState(true)
    const token = window.localStorage.getItem("token") || ''
    const decodedToken: any = jwt_decode(token)
    const uuid = decodedToken.uuid

    const isAuth = async () => {
        await instance.get(`/users/${uuid}`, {
            headers: {
                'Authorization': `Bearer ${token}`
            }
        }).then((res) => {
            console.log(res)
            if (res.status === 200) setIsLoggedIn(true)
            setIsChecking(false);
            return;
        })
    }

    useEffect(() => {
        isAuth()
    }, [isLoggedIn])

    if(isChecking) return <p>Checking....</p>

    return isLoggedIn ? <Outlet /> : <Navigate to={'/connexion'} />
}

Javascript相关问答推荐

如何在ReactJS中修复这种不需要的按钮行为?

想要检测字符串中的所有单词

在shiny 模块中实现JavaScript

从外部访问组件变量-Vueejs

一次仅播放一个音频

*ngFor和@代表输入decorator 和选角闭合

如何为GrapesJS模板编辑器创建自定义撤销/重复按钮?

如何在Javascript中的控制台上以一行形式打印循环的结果

Snowflake JavaScript存储过程返回成功,尽管预期失败

嵌套异步JavaScript(微任务和macrotask队列)

我正在建立一个基于文本的游戏在react ,我是从JS转换.我怎样才能使变量变呢?

编剧如何获得一个div内的所有链接,然后判断每个链接是否都会得到200?

<;img>;标记无法呈现图像

try 将Redux工具包与MUI ToggleButtonGroup组件一起使用时出错

有没有一种直接的方法可以深度嵌套在一个JavaScript对象中?

当我点击一个按钮后按回车键时,如何阻止它再次被点击

如何在Java脚本中对数据进行签名,并在PHP中验证签名?

有没有办法通过使用不同数组中的值进行排序

通过解构/功能组件接收props-prop验证中缺少错误"

如何将字符串拆分成单词并跟踪每个单词的索引(在原始字符串中)?