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

Next.js中Firebase getDocs()仅返回集合首条文档问题求助

Firestore places集合查询仅返回首条文档问题修复

问题定位

  • 核心错误在状态更新逻辑:循环遍历查询结果时多次调用setCurrentPlaces,每次调用都读取闭包中缓存的初始currentPlaces值,没有拿到前一次更新后的最新状态,最终只会保留最后一次循环的赋值结果;且首次判断分支直接将单个文档对象赋值给状态,没有包裹为数组,后续数组展开逻辑会直接失效。
  • useEffect存在依赖缺失问题:登录用户对象未加入依赖数组,组件首次挂载时如果鉴权状态还未初始化完成,用户uid为空会导致查询条件异常。
  • 现有安全规则、数据库结构均无问题:查询携带的UserID等值匹配条件和安全规则的读权限约束完全匹配,不会触发权限拦截;根级places集合结构符合该查询的路径要求。

修复后代码

import { app, auth } from '../firebase'
import { getFirestore, collection, addDoc, getDocs, getDoc, setDoc, where, query } from 'firebase/firestore'
import { useEffect, useState } from 'react'

// 初始化状态直接用空数组,不要使用undefined作为初始值
const [currentPlaces, setCurrentPlaces] = useState([])

useEffect(() => {
  // 鉴权未完成时终止执行,避免发起无效查询
  if (!auth.currentUser?.uid) return
  const fetchPlaces = async () => {
    const db = getFirestore(app)
    const placesQuery = query(
      collection(db, 'places'), 
      where('UserID', '==', auth.currentUser.uid)
    )
    const querySnapshot = await getDocs(placesQuery)
    // 批量提取所有文档数据,一次性更新状态,避免循环内重复触发重渲染
    const result = querySnapshot.docs.map(doc => ({
      docId: doc.id, // 建议存储文档ID,后续更新、删除操作需要用到
      ...doc.data()
    }))
    setCurrentPlaces(result)
  }
  fetchPlaces()
}, [auth.currentUser?.uid])

数据库结构参考

Firestore数据库结构示意图

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.29 19:24:25