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

MUI X Data Grid传入getRowId仍提示行缺少唯一id报错

问题原因

报错由两个核心问题触发:

  • 遍历Firestore返回的文档集合时,在循环内逐次调用setRows更新状态:
    • 每次状态更新都会触发组件重渲染,DataGrid会在数据未完全加载的中间状态多次渲染,只要过程中出现id缺失、重复就会直接抛错
    • React 18 严格模式下useEffect会默认执行两次,这种逐次追加数组的写法会导致所有管理员数据被重复插入两次,直接造成id重复
  • 存在潜在id缺失风险:如果admins集合中有任意文档未配置email字段,对应行的id会是undefined,多个缺失email的文档会出现重复id,触发组件的id唯一性校验。
修复方案

不要在循环内逐次更新状态,先一次性遍历组装好所有行数据,再单次调用setRows完成状态更新,同时增加id兜底逻辑避免字段缺失导致的异常,修改后的useEffect代码如下:

useEffect(() => {
  const getAdmins = async () => {
    const adminsSnapshot = await getDocs(collection(db, "admins"));
    // 一次性组装所有行数据,避免循环内多次触发状态更新
    const adminRows = adminsSnapshot.docs.map((doc) => {
      const data = doc.data();
      return {
        // 优先使用email作为行id,email缺失时用Firestore自带的文档唯一id兜底,保证全局唯一
        id: data.email || doc.id,
        name: data.name,
        email: data.email,
        roles: data.roles,
        isSuspended: data.isSuspended,
        lastUpdated: data.lastUpdated,
        updatedByEmail: data.updatedByEmail,
      };
    });
    setRows(adminRows);
  };

  getAdmins();
}, []);

补充说明:你代码中配置的getRowId={(row) => row.email}本身写法没有问题,但因为上述状态更新逻辑的缺陷,DataGrid在中间渲染阶段拿到的rows数组本身就存在重复/缺失id的问题,所以即使配置了getRowId依然会报错。使用上述一次性组装数据+id兜底的逻辑后,甚至可以省略手动配置的getRowId属性,因为行数据本身已经携带了唯一id字段。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 10:39:19