React报Objects are not valid as a React child错误,react-router-dom v6私有路由实现问题
错误成因
React 的组件函数不能是 async 异步函数。你给 PrivateRoute 加了 async 关键字之后,函数的返回值会自动包裹为 Promise 对象,而 React 不能直接把 Promise 作为子元素渲染,这就是你看到Objects are not valid as a React child (found: [object Promise])报错的直接原因。
修复方案
你需要把异步校验逻辑放到 useEffect 钩子中执行,配合状态管理判断渲染内容,改造后的代码参考:
import { Navigate } from 'react-router-dom'; import { useSelector } from 'react-redux'; import { useState, useEffect } from 'react'; import { isLogged } from '../helpers/isLogged'; export const PrivateRoute = ({children}) => { const userData = useSelector(store => store.user.object); // 新增两个状态:校验加载态、登录结果态 const [isLoading, setIsLoading] = useState(true); const [isLoggedIn, setIsLoggedIn] = useState(false); useEffect(() => { // 把异步逻辑放到useEffect内部执行 const checkAuth = async () => { const logged = await isLogged(userData); setIsLoggedIn(logged); setIsLoading(false); }; checkAuth(); }, [userData]); // userData变化时重新校验 // 校验过程中可以返回加载提示,避免页面闪烁 if (isLoading) return <div>权限校验中...</div>; return isLoggedIn ? children : <Navigate to="/login" />; }
使用注意
- 在路由配置中直接用该组件包裹受保护的路由即可,符合 react-router-dom v6 的嵌套路由使用规范
- 如果 isLogged 方法没有特殊的异步逻辑(比如不需要调用接口校验 token 有效性),可以直接去掉 async/await,不用加状态和 useEffect,代码会更简洁
内容的提问来源于stack exchange,提问作者Salvador Bacci
相关产品推荐
相关产品推荐

