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

React Router v6中Context传递给Link仅获默认值的解决方法

React Router v6中Context传递失效的解决方案

核心问题

你遇到的问题根源是:跳转后的目标组件不在更新后Context Provider的组件树范围内。React Context是靠组件层级传递的,只有Provider的子组件才能拿到它的值,而你之前把更新后的Provider只放在了Masthead内部,跳转后的/pronosticos组件是由Router直接渲染的,不在这个层级里,所以只能拿到默认的Context值。

具体解决步骤

1. 用嵌套路由统一管理需要共享Context的页面

修改App.js,把需要访问登录后Context的路由都放在一个父路由下,用React Router v6的<Outlet/>来渲染子路由,这样所有子路由组件都会成为父组件的子元素,自然能继承父组件提供的Context。

修改后的App.js:

import { Router, Routes, Route } from 'react-router-dom';
import { UserContext } from './Context';
import Login from './Login';
import AuthLayout from './AuthLayout';

// ...其他代码

return (
  <UserContext.Provider value={{ teams, groupMatches, getImg }}>
    <div id="page-top">
      <Router>
        <Routes>
          <Route path="/login" element={<Login />} />
          {/* 所有需要登录的页面都放在这个父路由下 */}
          <Route path="/" element={<AuthLayout />}>
            <Route index element={<Masthead />} /> {/* 原首页路由 */}
            <Route path="/pronosticos" element={<Pronosticos />} /> {/* 目标路由 */}
          </Route>
        </Routes>
      </Router>
    </div>
  </UserContext.Provider>
);

2. 新建AuthLayout组件处理登录状态和Context更新

这个组件负责判断用户是否登录,并提供包含用户信息的Context,所有嵌套在它下面的路由组件都能拿到这个更新后的值。

AuthLayout.js:

import { useContext, useState, useEffect } from 'react';
import { Outlet, Navigate } from 'react-router-dom';
import { UserContext } from './Context';

const AuthLayout = () => {
  const [userLogged, setUserLogged] = useState(null);
  const { teams, groupMatches, getImg } = useContext(UserContext);

  // 这里替换成你实际获取登录用户的逻辑(比如从localStorage/接口拿)
  useEffect(() => {
    const savedUser = localStorage.getItem('user');
    if (savedUser) {
      setUserLogged(JSON.parse(savedUser));
    }
  }, []);

  // 未登录就跳转到登录页
  if (!userLogged) {
    return <Navigate to="/login" />;
  }

  // 给子路由提供包含用户信息的Context
  return (
    <UserContext.Provider
      value={{
        id: userLogged.id,
        userInfo: userLogged,
        teams,
        groupMatches,
        getImg,
      }}
    >
      {/* Outlet会自动渲染当前匹配的子路由组件(比如Masthead或Pronosticos) */}
      <Outlet />
    </UserContext.Provider>
  );
};

export default AuthLayout;

3. 简化Masthead和Navigation组件

现在不需要在这两个组件里重复包裹Provider了,直接用useContext拿值就行:

修改后的Masthead.js:

import { useContext } from 'react';
import { UserContext } from './Context';
import Navigation from './Navigation';

const Masthead = () => {
  const { groupMatches } = useContext(UserContext);

  // 登录判断已经在AuthLayout里做了,这里直接渲染内容
  return (
    <>
      <Navigation />
      {/* 你的Masthead其他内容 */}
    </>
  );
};

export default Masthead;

修改后的Navigation.js:

import { useContext } from 'react';
import { Link } from 'react-router-dom';
import { UserContext } from './Context';

const Navigation = () => {
  const { id, userInfo, teams, groupMatches, getImg } = useContext(UserContext);

  return (
    <nav>
      {/* 直接用Link,不需要额外包裹Provider */}
      <Link to="/pronosticos" className="nav-link">Pronosticos</Link>
      {/* 其他导航链接 */}
    </nav>
  );
};

export default Navigation;

4. 目标组件Pronosticos获取Context值

现在Pronosticos组件可以直接拿到更新后的Context值了:

import { useContext } from 'react';
import { UserContext } from './Context';

const Pronosticos = () => {
  const { id, userInfo, teams, groupMatches, getImg } = useContext(UserContext);

  return (
    <div>
      <h1>Pronosticos页面</h1>
      <p>当前用户ID:{id}</p>
      {/* 你的页面内容 */}
    </div>
  );
};

export default Pronosticos;

关键逻辑说明

  • React Context是组件树层级传递的,只有Provider的子组件才能读取它的值,嵌套路由刚好解决了路由组件不在同一层级的问题。
  • 把登录判断和Context更新放在父路由组件里,避免了在多个子组件里重复写相同逻辑,也保证了所有需要的页面都能拿到正确的Context值。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.20 09:23:09