ReactJS拆分组件至独立页面时无法识别函数、组件不渲染
问题原因
组件无法正常渲染是两个基础写法错误导致的:
- 违反React组件命名强制规则:React要求所有用户自定义组件必须大写英文字母开头,小写开头的标签会被框架直接识别为原生HTML标签,不会执行组件加载、渲染逻辑。你定义的
newcreate、add都是小写开头,引入使用时React根本不会把它们当成组件处理。 - addpeople.js组件结构写法错误:你现在写的
newcreate函数内部返回的是另一个App函数的定义,而React函数组件的要求是直接返回可渲染的JSX结构,这种嵌套返回函数的写法相当于组件没有合法的渲染输出,自然无法正常加载。
修复步骤
- 修正addpeople.js的组件结构,去掉多余的嵌套函数,将组件重命名为大写开头的
NewCreate,同时清理无用导入,修正员工列表展示时未绑定变量、列表项缺少key、state初始值类型不统一的小问题,修复后代码如下:
import React, { useState } from 'react'; import "./add.css"; import Axios from "axios"; import 'bootstrap/dist/css/bootstrap.min.css'; function NewCreate() { const [surename_ru, setSurename_ru] = useState(""); const [name_ru, setName_ru] = useState(""); const [fname_ru, setFname_ru] = useState(""); const [surename_en, setSurename_en] = useState(""); const [name_en, setName_en] = useState(""); const [gender, setGender] = useState(""); const [dateofbirth, setDateofbirth] = useState(""); const [citizenship, setCitizenship] = useState(""); const [pas_ser, setPas_ser] = useState(""); const [pas_num, setPas_num] = useState(""); const [pas_start, setPas_start] = useState(""); const [pas_end, setPas_end] = useState(""); const [pas_given, setPas_given] = useState(""); const [pas_givenkod, setPas_givenkod] = useState(""); const [inn_num, setInn_num] = useState(""); const [snils_num, setSnils_num] = useState(""); const [legal_type, setLegal_type] = useState(""); const [newWage, setNewWage] = useState(0); const [employeeList, setEmployeeList] = useState([]); const addEmployee = () => { Axios.post("http://localhost:3001/create", { surename_ru, name_ru, fname_ru, surename_en, name_en, gender, dateofbirth, citizenship, pas_ser, pas_num, pas_start, pas_end, pas_given, pas_givenkod, inn_num, snils_num, legal_type, }).then(() => { setEmployeeList([ ...employeeList, {surename_ru, name_ru, fname_ru, surename_en, name_en, gender, dateofbirth, citizenship, pas_ser, pas_num, pas_start, pas_end, pas_given, pas_givenkod, inn_num, snils_num, legal_type} ]); }); }; const getEmployees = () => { Axios.get("http://localhost:3001/employees").then((response) => { setEmployeeList(response.data); }); }; const updateEmployeeWage = (id) => { Axios.put("http://localhost:3001/update", { wage: newWage, id }).then( () => { setEmployeeList( employeeList.map((val) => val.id == id ? {...val} : val ) ); } ); }; const deleteEmployee = (id) => { Axios.delete(`http://localhost:3001/delete/${id}`).then(() => { setEmployeeList(employeeList.filter((val) => val.id != id)); }); }; return ( <div className="App"> <div className="information"> <label>Фамилия</label> <input type="text" onChange={(e) => setSurename_ru(e.target.value)} /> <label>Имя РУС</label> <input type="text" onChange={(e) => setName_ru(e.target.value)} /> <label>Отчество</label> <input type="text" onChange={(e) => setFname_ru(e.target.value)} /> <label>Surename EN</label> <input type="text" onChange={(e) => setSurename_en(e.target.value)} /> <label>Name EN</label> <input type="text" onChange={(e) => setName_en(e.target.value)} /> <label>gender</label> <input type="text" onChange={(e) => setGender(e.target.value)} /> <label>Data ROJD</label> <input type="text" onChange={(e) => setDateofbirth(e.target.value)} /> <label>Citizenship</label> <input type="text" onChange={(e) => setCitizenship(e.target.value)} /> <label>Pas SER</label> <input type="text" onChange={(e) => setPas_ser(e.target.value)} /> <label>Pas NUM</label> <input type="text" onChange={(e) => setPas_num(e.target.value)} /> <label>Pas Start</label> <input type="text" onChange={(e) => setPas_start(e.target.value)} /> <label>Pas End</label> <input type="text" onChange={(e) => setPas_end(e.target.value)} /> <label>Pas Given</label> <input type="text" onChange={(e) => setPas_given(e.target.value)} /> <label>Pas Givenkod</label> <input type="text" onChange={(e) => setPas_givenkod(e.target.value)} /> <label>inn_num</label> <input type="text" onChange={(e) => setInn_num(e.target.value)} /> <label>snils_num</label> <input type="text" onChange={(e) => setSnils_num(e.target.value)} /> <label>legal Type</label> <input type="text" onChange={(e) => setLegal_type(e.target.value)} /> <button onClick={addEmployee}>Add Employee</button> </div> <div className="employees"> <button onClick={getEmployees}>Show Employees</button> {employeeList.map((val, key) => { return ( <div className="employee" key={val.id || key}> <div> <h3>surename_ru: {val.surename_ru}</h3> <h3>name_ru: {val.name_ru}</h3> <h3>fname_ru: {val.fname_ru}</h3> <h3>surename_en: {val.surename_en}</h3> <h3>name_en: {val.name_en}</h3> <h3>gender: {val.gender}</h3> <h3>dateofbirth: {val.dateofbirth}</h3> <h3>citizenship: {val.citizenship}</h3> <h3>pas_ser: {val.pas_ser}</h3> <h3>pas_num: {val.pas_num}</h3> <h3>pas_start: {val.pas_start}</h3> <h3>pas_end: {val.pas_end}</h3> <h3>pas_given: {val.pas_given}</h3> <h3>pas_givenkod: {val.pas_givenkod}</h3> <h3>inn_num: {val.inn_num}</h3> <h3>snils_num: {val.snils_num}</h3> <h3>legal_type: {val.legal_type}</h3> </div> <div> <input type="text" placeholder="2000..." onChange={(e) => setNewWage(e.target.value)} /> <button onClick={() => updateEmployeeWage(val.id)}> Update </button> <button onClick={() => deleteEmployee(val.id)}> Delete </button> </div> </div> ); })} </div> </div> ); } export default NewCreate;
- 修正add.js的组件命名和引入使用方式,将页面组件重命名为大写开头的
Add,引入组件时使用大写标签渲染,修复后代码如下:
import React from 'react'; import NewCreate from './addpeople'; function Add() { return ( <div> <NewCreate /> </div> ); } export default Add;
补充说明:原代码中导入的
Component、Button都没有实际使用,属于冗余导入,修复时已经一并清理。
内容的提问来源于stack exchange,提问作者Russiasolo
相关产品推荐
相关产品推荐

