You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React JS中token为空时调用navigate跳转/login报错如何解决

问题描述

在React JS项目中需要实现:当localStorage中存储的token为空时,自动跳转至/login登录页,实际运行时出现报错:

You should call navigate() in a React.useEffect(), not when your component is first rendered.

对应出问题的原始Main.js代码:

function Main() {
  const token = localStorage.getItem("token");
  const navigate = useNavigate();

  if (token == null) {
    navigate("/login");
  }
  return (
    <div>
      {token && <AdminHeader />}
      <Routes>
        <Route path="/" element={<HomePage />}></Route>
        <Route path="/login" element={<Login />}></Route>
        <Route path="/admin/" element={token && <AdminPage />}>
          <Route path="/admin/add-post" element={token && <AddPost />}></Route>
          <Route
            path="/admin/update-post"
            element={token && <UpdatePost />}
          ></Route>
          <Route
            path="/admin/add-country"
            element={token && <AddCountry />}
          ></Route>
          <Route
            path="/admin/post-list"
            element={token && <ListPost />}
          ></Route>
        </Route>
      </Routes>
    </div>
  );
}

export default Main;
问题原因
  • 核心错误是在组件渲染的同步执行阶段直接调用了navigate()方法。React Router规定导航属于副作用操作,不能在组件首次渲染、函数组件同步执行的过程中触发,必须放到useEffect这类副作用钩子中执行,否则会打断React正常的渲染流程,触发上述报错。
  • 原代码中token && <AdminPage />这类写法存在逻辑漏洞:当token为空时,路由对应渲染的内容是null,页面会直接显示空白,不会按预期触发跳转。
  • 嵌套路由重复写全量路径/admin/xxx属于冗余写法,容易出现路径拼接错误。
修正方案
  1. 将token校验、跳转的逻辑全部移入useEffect钩子中,将token和navigate设为依赖项,保证token状态变化时自动执行校验逻辑
  2. 跳转时增加replace: true配置,替换当前路由栈记录,避免用户点击浏览器返回键时回到无权限的页面造成循环跳转
  3. 受保护路由使用<Navigate>组件做兜底重定向,替代原有的token && 组件写法,避免出现空白页
  4. 嵌套路由使用相对路径写法,减少路径书写错误

修正后的完整代码:

import { useEffect } from 'react';
import { Routes, Route, useNavigate, Navigate } from 'react-router-dom';
// 其他业务组件导入省略

function Main() {
  const token = localStorage.getItem("token");
  const navigate = useNavigate();

  // 导航副作用放到useEffect中执行
  useEffect(() => {
    if (!token) {
      navigate("/login", { replace: true });
    }
  }, [token, navigate]);

  return (
    <div>
      {token && <AdminHeader />}
      <Routes>
        <Route path="/" element={<HomePage />} />
        <Route path="/login" element={<Login />} />
        <Route 
          path="/admin" 
          element={token ? <AdminPage /> : <Navigate to="/login" replace />}
        >
          <Route path="add-post" element={<AddPost />} />
          <Route path="update-post" element={<UpdatePost />} />
          <Route path="add-country" element={<AddCountry />} />
          <Route path="post-list" element={<ListPost />} />
        </Route>
      </Routes>
    </div>
  );
}

export default Main;

内容的提问来源于stack exchange,提问作者Demi God

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.01 19:29:00