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

React Router PrivateRoute结合Firebase Auth登录后持续重定向到登录页问题

问题根源

你现在的问题主要是两个核心错误:

  1. PrivateRoute里没有用你已经写好的AuthContext的currentUser做判断,反而用了全局变量Cuser,这个变量只会在Signup组件渲染的时候才会被赋值,路由切换的时候根本不会同步更新,而且初始值是null,页面刚加载的时候直接就跳转到登录页了
  2. 没有处理Firebase Auth的初始化加载状态:Firebase初始化验证用户登录状态是异步的,在这个加载间隙currentUser是undefined,这时候你直接判断未登录就跳转,当然会出问题

修复步骤

  • 第一步:修改你的PrivateRoute组件,删掉没用的全局变量Cuser,增加加载状态判断:
const PrivateRoute = ({component: Component, ...rest}) => {
    const {currentUser} = useAuth()
    // 新增加载状态,currentUser为undefined时说明还在加载firebase auth状态,暂时不跳转
    const [isLoading, setIsLoading] = useState(true)

    useEffect(() => {
        // 等currentUser状态确定后(不管是已登录还是未登录),再结束加载
        setIsLoading(false)
    }, [currentUser])

    if (isLoading) {
        // 加载期间可以显示自定义加载提示,避免页面闪跳
        return <div>加载中...</div>
    }

    return (
      <Route {...rest} render={props => {
        return currentUser ? <Component {...props} /> : <Redirect to="/signin" />
      }} />
    )
}
  • 第二步:修复Signup组件的问题,给useEffect加空依赖数组避免重复监听,删掉没用的Cuser赋值:
const Signup = () => {
    const {history} = useHistory()
    const [user, setUser] = useState(null)
    // 加空依赖数组,只在组件挂载时监听一次登录状态
    useEffect(() => {
        const authOberver = firebase.auth().onAuthStateChanged((user) => {
            setUser(user)
            if (user) {
                axios.post("http://localhost:4000/notes", {
                  email: user.email,
                })
                // 登录成功后直接跳首页,不需要依赖全局变量
                history.push('/')
            }
        });
        return authOberver
    }, [history])
    
    return (
        <>
            <div>Signin / Register</div>
            <StyledFirebaseAuth uiConfig={uiconfig} firebaseAuth={firebase.auth()}></StyledFirebaseAuth>
        </>
    )
}
  • 第三步:确认根组件已经包裹了AuthProvider,否则useAuth拿不到上下文状态:
// 以App.js为例
import { AuthProvider } from './context/AuthContext'

function App() {
  return (
    <AuthProvider>
      {/* 所有路由、组件都要放在AuthProvider内部 */}
      <Router>
        <Switch>
          <Route path="/signin" component={Signup} />
          <PrivateRoute path="/" exact component={Home} />
        </Switch>
      </Router>
    </AuthProvider>
  )
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.07 01:48:03