如何将嵌套对象值正确映射到React的MUI X Data Grid
问题根因
你的代码存在3个直接导致表格无法正常渲染数据的错误:
- 数据映射逻辑错误:外层遍历赛事数组时,错误使用外层索引
i取events.Events[i],只能拿到每个赛事下对应索引的单个票档;同时两层map生成的是二维数组,而MUI Data Grid要求rows必须传入一维对象数组。另外内层箭头函数返回对象时没有用小括号包裹,大括号被解析为函数体边界,实际返回值为undefined。 - 字段映射不全:列配置声明了
amountLeft、url两个字段,但映射数据时只提取了seating和price,对应列会直接显示为空。 - 行ID生成逻辑异常:
getRowId返回Math.random()会导致组件每次重渲染时行ID都发生变化,引发行状态丢失、渲染错位等难以排查的问题。
可直接运行的修复代码
// 映射行数据:用flatMap直接拍平嵌套的Events数组,输出DataGrid需要的一维行数据列表 const nationwidePopoverRows = responseData.flatMap((event) => { return event.Events.map((ticket, idx) => ({ // 用赛事ID+票档序号生成固定唯一ID,避免随机ID导致的渲染问题 id: `${event.id}-${idx}`, seating: ticket.seating, // 顺手去除余票字段末尾的多余空格 amountLeft: ticket.amountLeft.trim(), price: ticket.price, url: ticket.url })) }) const nationWidePopoverColumns = [ {field: 'seating', headerName: 'SEATING LOCATION', flex: 1}, {field: 'amountLeft', headerName: 'TICKETS LEFT', flex: 1}, {field: 'price', headerName: 'TICKET PRICE', flex: 1}, { field: 'url', headerName: 'BUY TICKETS', flex: 1, // 自定义渲染购票链接,可根据需求调整样式 renderCell: (params) => ( <a href={params.value} target="_blank" rel="noreferrer">去购票</a> ) } ] // Popover内的DataGrid组件,移除有问题的getRowId,因为我们已经给每行加了组件默认识别的id字段 <Popover elevation={3} open={popover} anchorEl={anchorEl} onClose={handlePopoverClose} anchorOrigin={{vertical: 'bottom',horizontal: 'left'}} > <DataGrid autoHeight columns={nationWidePopoverColumns} pageSize={15} rows={nationwidePopoverRows} rowsPerPageOptions={[15]} /> </Popover>
注意事项
- 箭头函数直接返回对象字面量时,必须用小括号把对象包起来,否则JS引擎会把对象的大括号判定为函数体的开始/结束标记,不会返回预期的对象。
- MUI Data Grid的
rows属性只接受一维数组,遇到嵌套数组结构必须先拍平再传入。 - 行ID必须保证稳定性:同一行数据在组件全生命周期内ID不能变,禁止使用随机数、时间戳这类每次渲染都会变的值作为行ID。
- 如果交互逻辑是点击某一行赛事时,Popover只显示当前选中赛事的票档,不需要拍平所有数据,只需要在打开Popover时记录当前选中的赛事对象,直接取该对象的
Events数组映射为行数据即可。
内容的提问来源于stack exchange,提问作者NevrMore
相关产品推荐
相关产品推荐

