Firebase报Possible Unhandled Promise Rejection(id:2)错误排查
报错原因
ReferenceError: Can't find variable: ref和连带的Possible Unhandled Promise Rejection (id:2)报错由多类问题共同导致,具体如下:
- 代码变量引用错误:
getAvatar函数中获取文档快照后,错误调用了未在当前作用域定义的doc.data()、doc.id——此处doc是你从Firestore导入的引用构造函数,不是查询返回的快照对象,正确的快照变量是你定义的snap;同时函数内使用的avatars数组未提前声明,也会触发引用错误,直接影响用户名展示逻辑。 - 集合路径拼写错误:
addEntryToComp函数中写入子集合时,将全局统一的复数集合名comps错写为单数comp,会导致路径匹配失败抛出错误,影响竞赛条目提交逻辑。 - 查询逻辑错误:
getEntryOffComp函数中已经定义了对应竞赛下entries子集合的引用,实际调用getDocs时却传入了错误的根级entries集合路径,查询逻辑完全不匹配。 - 缺失导入:上传图片场景如果使用Firebase Storage实现,直接调用
ref()创建存储引用却未从firebase/storage导入对应方法,会直接触发ref变量未定义的错误。 - 无错误捕获:所有异步Promise方法调用时未设置catch捕获逻辑,错误抛出后就会触发未处理Promise拒绝的系统提示。
- 无效逻辑:
getAllComp函数直接返回collection引用,没有实际执行查询动作,调用时无法拿到预期的竞赛列表数据;从@firebase/util导入的async、querystring无任何使用场景,属于无效导入。
修复后完整Database.js代码
import { auth, db } from "./firebase"; import {doc, setDoc, Timestamp, collection, getDoc, getDocs,addDoc, onSnapshot} from 'firebase/firestore'; // 若使用Firebase Storage上传图片,需补充以下导入 // import { ref, uploadBytes, getDownloadURL } from 'firebase/storage'; // import { storage } from './firebase'; // 提前声明存储头像数据的数组 const avatars = []; export const createUserOnRegister = (user, username) => { const userRef = doc(db, 'avatars', user.uid); const userData = { email: user.email, username: username, uid: user.uid, role: 'student', dateCreated: Timestamp.fromDate(new Date()) } return setDoc(userRef, userData); } export const getAvatar = async () => { // 增加未登录场景判断,避免空值报错 if (!auth.currentUser) return null; const userRef = doc(db, "avatars", auth.currentUser.uid); const snap = await getDoc(userRef); // 增加文档存在性判断 if (!snap.exists()) return null; let avatar = {...snap.data(), uid: snap.id} avatars.push(avatar); return avatar; } export const updateProfile = (uid, data) => { const userRef = doc(db, 'avatars', uid) return setDoc(userRef, data, {merge: true}) } export const newComp = (comp) => { return addDoc( collection(db, 'comps'), comp ) } export const getAllComp = async () => { const compList = []; const querySnapshot = await getDocs(collection(db, "comps")); querySnapshot.forEach(doc => { compList.push({...doc.data(), id: doc.id}); }) return compList; } export const getEntryOffComp = async(id) => { let entries = [] // 保持集合名拼写统一为comps const collectionRef = collection(db, `comps/${id}/entries`) // 传入正确的子集合引用执行查询 const collectionSnapshot = await getDocs(collectionRef) collectionSnapshot.forEach((doc) => { entries.push({...doc.data(), id: doc.id}); }) return entries } export const addEntryToComp = (data, id) => { // 修正路径拼写为comps,和全局集合名保持一致 const collectionRef = collection(db, `comps/${id}/entries`) return addDoc(collectionRef, data) }
调用规范
所有返回Promise的异步方法调用时,必须添加错误捕获逻辑,避免触发未处理Promise拒绝提示,示例:
// 拉取用户信息展示用户名示例 getAvatar() .then(avatar => { if (avatar) { console.log('用户名:', avatar.username) // 执行用户名渲染逻辑 } }) .catch(err => { console.error('获取用户信息失败:', err) })
内容的提问来源于stack exchange,提问作者Jeandré De Villiers
相关产品推荐
相关产品推荐

