Firebase v9模块化开发报错:Expected type 'Ea', but it was: a custom Na object
解决Firebase v9监听订单数据的错误问题
错误原因分析
你的v9代码存在几个关键问题,导致了FirebaseError: Expected type 'Ea', but it was: a custom Na object错误:
- 集合/文档引用构建错误:原教程逻辑是
users集合→用户文档→orders子集合,但你用getDocs(db, "users", user?.id)的写法完全错误,不符合v9模块化的引用构建规则。 onSnapshot使用错误:onSnapshot是实时监听函数,不需要用await,它返回的是取消订阅的函数,而非Promise对象。- 数据处理逻辑顺序错误:你直接将原始快照赋值给
orders再去map,不仅逻辑颠倒,而且快照本身不是数组,无法直接执行map操作。
修正后的v9代码
const [orders, setOrders] = useState([]); useEffect(() => { let unsubscribe; if (user) { // 正确构建用户文档下的orders子集合引用 const userDocRef = doc(db, "users", user.id); const ordersCollRef = collection(userDocRef, "orders"); // 创建排序查询 const orderedQuery = query(ordersCollRef, orderBy("created", "desc")); // 正确使用onSnapshot实时监听数据 unsubscribe = onSnapshot(orderedQuery, (snapshot) => { // 格式化快照数据为需要的结构 const formattedOrders = snapshot.docs.map(doc => ({ id: doc.id, data: doc.data() })); setOrders(formattedOrders); }); } else { setOrders([]); } // 组件卸载时取消监听,避免内存泄漏 return () => { if (unsubscribe) unsubscribe(); }; }, [user]);
关键修正点说明
- 引用链对齐原教程逻辑:用
doc(db, "users", user.id)获取用户文档引用,再用collection(userDocRef, "orders")获取该文档下的orders子集合,和非模块化的链式调用逻辑完全对应。 - 规范
onSnapshot用法:去掉多余的await,通过回调函数处理实时更新的快照,同时保存返回的取消订阅函数,在组件卸载时调用以防止内存泄漏。 - 数据处理逻辑修正:在
onSnapshot的回调里直接处理snapshot.docs的map转换,再将格式化后的数组传入setOrders,和原教程的数据处理逻辑保持一致。
内容的提问来源于stack exchange,提问作者Victor Choe
相关产品推荐
相关产品推荐

