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

React项目状态提升失败:TypeError: props.onSaveStudioData不是函数

问题:React状态提升实现中表单提交报错「props.onSaveStudioData is not a function」

问题描述

学习React状态管理的「状态提升」时,实现表单提交工作室数据到App组件的功能,遇到报错:Form.jsx:58 Uncaught TypeError: props.onSaveStudioData is not a function,导致数据无法传递,始终卡在该错误。

已尝试的排查操作

  • 检查NewStudio和App组件的拼写,确认无错误
  • 将Form组件的单一状态拆分为多个状态,问题仍未解决
  • 将Form组件参数改为props,引发其他错误

组件代码

Form.jsx

export default function Form( props ) {
  const manilaCities = ["Bulacan", "Caloocan", "Navotas", "Pasig", "Parañaque", "Quezon City", "San Juan", "Taguig"];

  const [inputtedTitle, setTitle] = useState('')
  const [inputtedAddress, setAddress] = useState('')
  const [inputtedCity, setCity] = useState('')

  const titleChangeHandler = (event) => {
    setTitle(event.target.value);
};

const addressChangeHandler = (event) => {
    setAddress(event.target.value);
}

const cityChangeHandler = (event) => {
    setCity(event.target.value);
};

  const submitText = (event) => { 
    event.preventDefault();
    
    const studioData = {
      name: inputtedTitle,
      address: inputtedAddress,
      city: inputtedCity
    }

    props.onSaveStudioData(studioData);
    setTitle('');
    setAddress('');
    setCity('');
  }

  const cityOption = manilaCities.map((city, index) => <option key={index} value={city}> {city} </option>)
  return (
    <div>
      <form onSubmit={submitText} className={`bg-sky-500 flex flex-col p-8 m-12 text-center rounded-2xl ${props.isVisible ? "" : "hidden"} `}>
        <label htmlFor="">Studio Name</label>
        <input type="text" name="studio-name" value={inputtedTitle} onChange={titleChangeHandler} />
        <label htmlFor="">Address </label>
        <input type="text" name="Hey" value={inputtedAddress} onChange={addressChangeHandler} />
        <label htmlFor=""> City </label>
        <select value={inputtedCity} onChange={cityChangeHandler} >
          {cityOption}
        </select>
        <label htmlFor=""> Studio Image </label>
        <span className="m-1"><input type="file" name="Hey" id="" /></span>
        <span className="inline-block"><button type="submit" className="rounded-full bg-sky-50 py-2 px-4 m-1">Add Studio</button></span>
      </form>
    </div>
  );
}

NewStudio.jsx

import Form from '../Form';    
export default function NewStudio(props) {
    const saveStudioDataHandler = (enteredStudioData) => {
        const studioData = {
            ...enteredStudioData,
            id: Math.random().toString()
        };
       props.onAddStudio(studioData);
    }

    return (
    <div>
        <Form onSaveStudioData = {saveStudioDataHandler} />
    </div>
  )
}

App.jsx

import Form from './components/Form';
import StudioList from './components/Studios/StudioList'
import { useState } from 'react';
import NewStudio from './components/Studios/NewStudio';

export default function App() {
  const [isFormVisible, setIsFormVisible] = useState(false);
  const toggleFormVisibility = () => {
    setIsFormVisible(!isFormVisible);
  }

  const addStudioHandler = (studio) => {
    console.log('In App.js')
    console.log(studio);
  }

  return (
    <div>
      <Nav toggleForm={toggleFormVisibility}/>
      <NewStudio onAddStudio={addStudioHandler}/>
      <Hero/>
      <Form isVisible={isFormVisible} />
      <StudioList/>
    </div>
  )
}

解决方案

问题根源是App组件中重复渲染了两个Form实例:

  1. 一个通过NewStudio组件渲染,带有onSaveStudioData回调函数
  2. 另一个直接在App中渲染,仅传入了isVisible属性,未传递onSaveStudioData

当用户操作的是第二个Form实例时,提交表单就会触发props.onSaveStudioData,但该属性不存在,因此抛出类型错误。

修复步骤:

  1. 删除App组件中直接渲染的<Form isVisible={isFormVisible} />
  2. 将isVisible状态传递给NewStudio组件,再由NewStudio转发给Form

修改后的代码:

修改App.jsx的return部分
return (
  <div>
    <Nav toggleForm={toggleFormVisibility}/>
    <NewStudio onAddStudio={addStudioHandler} isVisible={isFormVisible}/>
    <Hero/>
    <StudioList/>
  </div>
)
修改NewStudio.jsx
import Form from '../Form';    
export default function NewStudio(props) {
    const saveStudioDataHandler = (enteredStudioData) => {
        const studioData = {
            ...enteredStudioData,
            id: Math.random().toString()
        };
       props.onAddStudio(studioData);
    }

    return (
    <div>
        <Form onSaveStudioData={saveStudioDataHandler} isVisible={props.isVisible} />
    </div>
  )
}

这样就能确保所有使用的Form实例都具备onSaveStudioData回调,表单提交后数据可以正常通过状态提升传递到App组件。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.12 04:55:01