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

React Firebase博客:ViewPosts子组件向App父组件传值报错解决

React子组件向父组件传递状态的问题解决

问题描述

我正在构建一个React Firebase博客,想要将子组件ViewPosts中的color状态传递给父组件App,但点击按钮时持续收到错误:

Uncaught TypeError: props.setBackgroundColor is not a function

App组件代码

function App() {
  const [backgroundColor, setBackgroundColor] = useState("");

  return (
    <div className="app" style={{ background: backgroundColor }}>
      <Router>
        <Routes>
          <Route path="/" element={<Login />} />
          <Route path="/register" element={<Register />} />
          <Route path="/reset" element={<Reset />} />
          <Route path="/dashboard" element={<Dashboard />} />
          <Route path="/view-posts" element={<ViewPosts setBackgroundColor={setBackgroundColor} />} />
          <Route path="/create-post" element={<CreatePost />} />
          <Route path="/edit-post/:id" element={<EditPost />} />
          <Route path="/profile/:id" element={<Profile />} />
        </Routes>
      </Router>
    </div>
  );
}

export default App;

ViewPosts核心代码

const ViewPosts = props => {
    const [color, setColor] = useState("");

    return (
        <Container>
            {/* 其他代码 */}
            <input
                id="search-bar"
                type="text"
                value={color}
                onChange={(e) => setColor(e.target.value)}
            />
            <button
                className="view-post-button"
                onClick={() => props.setBackgroundColor(color)}
            >
                Change background
            </button>
            {/* 其他代码 */}
        </Container>
    );
};

export default ViewPosts;

问题原因与解决方案

1. 核心原因:Props传递被拦截(最常见情况)

如果你的ViewPosts组件被高阶组件(比如登录验证的HOC)包裹,高阶组件没有将接收到的props传递给目标组件,就会导致setBackgroundColor无法到达ViewPosts。

2. 解决方案

方案一:确保高阶组件传递所有Props

假设你有一个用于登录验证的高阶组件requireAuth,修改它以传递props:

const requireAuth = (Component) => {
  // 接收外部传入的props
  return (props) => {
    const [user, loading] = useAuthState(auth);
    
    if (loading) return <div>Loading...</div>;
    if (!user) return <Navigate to="/" />;

    // 将所有props传递给目标组件
    return <Component {...props} />;
  };
};

然后导出ViewPosts时使用该HOC:

export default requireAuth(ViewPosts);

方案二:明确解构接收Props

修改ViewPosts组件的props接收方式,用解构更直观,同时避免拼写错误:

// 直接解构出setBackgroundColor
const ViewPosts = ({ setBackgroundColor }) => {
    const [color, setColor] = useState("");

    return (
        <Container>
            {/* 其他代码 */}
            <button
                className="view-post-button"
                // 直接调用解构后的函数
                onClick={() => setBackgroundColor(color)}
            >
                Change background
            </button>
            {/* 其他代码 */}
        </Container>
    );
};

方案三:移除多余的exact属性

React Router v6中路由默认是精确匹配,exact属性已被移除,虽然这不是报错的直接原因,但移除后可以避免潜在的路由匹配问题:

// 原代码中的<Route exact path="/view-posts" ... />修改为
<Route path="/view-posts" element={<ViewPosts setBackgroundColor={setBackgroundColor} />} />

验证方法

在ViewPosts组件中添加日志,查看props内容:

const ViewPosts = props => {
    console.log("ViewPosts props:", props); // 检查是否包含setBackgroundColor
    // 其他代码
};

如果日志中没有setBackgroundColor,说明props在传递过程中丢失,优先检查高阶组件的包裹逻辑。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.03 02:06:06