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

React路由中Invalid Hook call错误的排查与解决

React路由使用中遇到无效Hook调用错误

错误信息

Error: Invalid hook call. Hooks can only be called inside of the body of a function component. This could happen for one of the following reasons:
1. You might have mismatching versions of React and the renderer (such as React DOM)
2. You might be breaking the Rules of Hooks
3. You might have more than one copy of React in the same app
See https://reactjs.org/link/invalid-hook-call for tips about how to debug and fix this problem.
    at Object.throwInvalidHookError (react-dom.development.js:16227:1)
    at Object.useContext (react.development.js:1618:1)
    at useInRouterContext (hooks.tsx:85:1)
    at Navigate (components.tsx:196:1)
    at Login.jsx:24:1

项目组件代码

Login.jsx

import React, { useState } from "react";
import { useLocation } from "react-router-dom";
import { Navigate } from "react-router-dom";

const Login = () => {
  const location = useLocation();
  const [email, setEmail] = useState("");
  const [password, setPassword] = useState("");
  const [errorMessage, setErrorMessage] = useState("");

  const submitForm = (event) => {
    event.preventDefault();
    fetch("http://localhost:8000/users")
      .then((response) => response.json())
      .then((data) => {
        const user = data.find(
          (user) =>
            user.email &&
            user.email.toLowerCase() === email.toLowerCase() &&
            user.password &&
            user.password.toLowerCase() === password.toLowerCase()
        );
        if (user) {
          Navigate("/profile");
        } else {
          setErrorMessage("Invalid email or password");
        }
      })
      .catch((error) => console.log(error));
  };

  return (
    <div>
      <form onSubmit={submitForm}>
        <div>
          <label htmlFor="email">Enter Email Address:</label>
          <input
            type="text"
            name="email"
            id="email"
            value={email}
            onChange={(e) => setEmail(e.target.value)}
          />
        </div>
        <div>
          <label htmlFor="password">Enter Password:</label>
          <input
            type="password"
            name="password"
            id="password"
            value={password}
            onChange={(e) => setPassword(e.target.value)}
          />
        </div>
        <button type="submit">Login</button>
      </form>
      {errorMessage && <p>{errorMessage}</p>}
    </div>
  );
};

export default Login;

App.jsx

import React from "react";
import { BrowserRouter as Router, Routes, Route } from "react-router-dom";
import Profile from "./components/Profile";
import Login from "./components/Login";

function App() {
  return (
    <div className="wrapper">
      <h1>Application</h1>
      <Router>
        <Routes>
          <Route path="/" element={<Login />} />
          <Route path="/profile" element={<Profile />} />
        </Routes>
      </Router>
    </div>
  );
}

export default App;

Profile.jsx

import React from "react";

const Profile = () => {
  return (
    <div>
      <h2>Dashboard</h2>
      <p>Welcome to your profile page!</p>
      {/* Display user profile information here */}
    </div>
  );
};

export default Profile;

已尝试的修复方法

  • 重装VSCode/Node.js
  • 新建React项目
  • 使用npm link ../myapp/node_modules/react命令

当前React版本信息

PS C:\Users\Admin\Documents\SD Semester2\Final_Sprint\finalsprint> npm ls react
finalsprint@0.1.0 C:\Users\Admin\Documents\SD Semester2\Final_Sprint\finalsprint
├─┬ @testing-library/react@13.4.0
├─┬ react-dom@18.2.0
│ └── react@18.2.0 deduped
├─┬ react-router-dom@6.10.0
│ └── react@18.2.0 deduped
├─┬ react-router@6.10.0
│ └── react@18.2.0 deduped
├─┬ react-scripts@5.0.1
│ └── react@18.2.0 deduped
└── react@18.2.0

另外,在浏览器控制台执行React.version时提示React未定义。


问题原因与修复方案

核心问题

你在Login组件的submitForm函数里直接调用Navigate("/profile"),但Navigate是React组件,不是普通函数。这种调用方式会触发组件内部的Hook执行,而Hook只能在函数组件的顶层作用域调用,违反了Hook规则,因此抛出错误。

修复步骤

  1. 替换Navigate导入为useNavigate钩子:
    import { useLocation, useNavigate } from "react-router-dom";
    
  2. 在Login组件顶层初始化导航函数:
    const Login = () => {
      const location = useLocation();
      const navigate = useNavigate(); // 新增此行
      // ...其他状态定义
    
  3. 修改登录成功后的跳转逻辑,使用navigate函数:
    if (user) {
      navigate("/profile"); // 替换原来的Navigate("/profile")
    }
    

额外说明

浏览器控制台无法访问React是因为生产环境下React会被压缩且不暴露全局变量,开发环境可通过window.React查看,但这和当前Hook错误无关。你的版本信息显示所有依赖的React版本一致,不存在多版本或版本不匹配的问题,核心问题就是错误使用Navigate组件。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.25 00:47:55