React MUI X Data Grid编辑异常:无法退出编辑模式及TypeError报错求助
问题原因与修复方案
1. 无法退出编辑模式
processRowUpdate 要求必须返回更新后的行数据,DataGrid 才会确认编辑完成并退出编辑状态。当前处理函数未返回值,导致组件一直停留在编辑模式。
2. TypeError: Cannot read properties of undefined (reading 'id')
- 对
processRowUpdate参数结构理解错误:更新后的行数据在参数的row属性中,而非直接取params.id; - 直接修改 state 中原数组
punteos,违反 React 不可变数据原则,同时固定循环12次,当数组长度不足时会访问undefined的id属性; - 未显式指定
getRowId属性,可能导致 DataGrid 无法正确识别行的唯一标识。
修改后的完整代码
import React, { Component } from "react" import ScoreDataService from "../../services/score.service"; import { Link } from "react-router-dom"; import { DataGrid } from '@mui/x-data-grid'; export default class StudentList extends Component { constructor(props) { super(props); this.ObtenerPunteos = this.ObtenerPunteos.bind(this); this.GuardarPunteos = this.GuardarPunteos.bind(this); this.Reset = this.Reset.bind(this); this.state = { punteos: [], punteos_viejos: [], isUpdated: false, }; } componentDidMount() { this.ObtenerPunteos(); } Reset(){ this.setState(prevState => ({ punteos: prevState.punteos_viejos, isUpdated: false })); } ObtenerPunteos() { ScoreDataService.getAll(7) .then(response => { this.setState({ punteos: response.data, punteos_viejos: response.data }); }) .catch(e => { console.log(e); }); } GuardarPunteos(){ const { punteos } = this.state; // 替换为你的后端批量更新接口 ScoreDataService.updateAll(punteos) .then(() => { this.setState({ punteos_viejos: punteos, isUpdated: false }); }) .catch(e => { console.log(e); }); } handleEditCellChange = ({ row }) => { // 生成新数组,遵循不可变数据原则 const updatedPunteos = this.state.punteos.map(item => item.id === row.id ? { ...item, ...row } : item ); this.setState({ punteos: updatedPunteos, isUpdated: true }); // 返回更新后的行,让DataGrid确认编辑完成 return row; }; handleProcessRowUpdateError = (error) => { console.log('编辑更新错误:', error); }; render() { const { punteos, isUpdated } = this.state; const columns = [ { field: 'id', headerName: 'id', width: 70, editable: false }, { field: 'curso', headerName: 'Curso', width: 200, editable: false }, { field: 'nota1', headerName: 'Bimestre 1', width: 130, editable: true, type: 'number'}, { field: 'nota2', headerName: 'Bimestre 2', width: 130, editable: true, type: 'number'}, { field: 'nota3', headerName: 'Bimestre 3', width: 130, editable: true, type: 'number' }, { field: 'nota4', headerName: 'Bimestre 4', width: 130, editable: true, type: 'number' }, ]; return( <div style={{ height: 800, width: '100%' }}> {punteos.length > 0 ? ( <DataGrid rows={punteos} columns={columns} pageSize={5} rowsPerPageOptions={[5]} processRowUpdate={this.handleEditCellChange} onProcessRowUpdateError={this.handleProcessRowUpdateError} getRowId={(row) => row.id} /> ) : ( <div>加载中...</div> )} <button onClick={this.GuardarPunteos} disabled={!isUpdated}>保存</button> <button onClick={this.Reset} disabled={!isUpdated}>重置</button> </div> ); } }
关键修改点说明
- 退出编辑模式修复:在
handleEditCellChange末尾返回更新后的row,让DataGrid确认编辑完成; - TypeError修复:
- 正确解构参数,从
row中获取更新后的数据; - 使用
map生成新数组,避免直接修改原state数组,同时遍历所有数组元素而非固定次数; - 显式配置
getRowId,确保DataGrid正确识别行唯一标识;
- 正确解构参数,从
- 功能优化:
- 重置功能直接恢复为原始备份数据;
- 移除
componentDidMount中不必要的函数调用; - 完善保存逻辑,添加后端接口调用,保存成功后更新原始数据备份。
内容的提问来源于stack exchange,提问作者Javier Morales
相关产品推荐
相关产品推荐

