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

React Native中无法读取Firestore用户文档数据问题排查

React Native 中无法读取Firestore用户文档数据的问题

在React Native应用中尝试根据已登录用户获取个人资料名称时,能访问到用户文档对象,但无法读取其中的数据。

相关代码

import React, { useState, useEffect } from 'react';
import { View, Text, StyleSheet } from 'react-native';
import { app, auth } from '../firebaseconfig';
import { getFirestore, doc, getDoc } from 'firebase/firestore';

const db = getFirestore(app);

const MainPage = () => {
  const [userName, setUserName] = useState('');

  useEffect(() => {
    const fetchUserData = async () => {
      try {
        const user = auth.currentUser;
        console.log('current user UID is:', user.uid);
    
        if (user) {
          const userDocRef = doc(db, 'users', user.uid);
          console.log('The doc is:', userDocRef);
    
          const userDocSnapshot = await getDoc(userDocRef);
          console.log('User document:', userDocSnapshot);
    
          if (userDocSnapshot) {
            console.log('User document exists:', userDocSnapshot.data());
            
            // Check if userData and userData.name exist before setting the state
            const userData = userDocSnapshot.data();
            if (userData && 'name' in userData) {
              setUserName(userData.name);
              console.log('Name property found:', userData.name);
            } else {
              console.log('Name property not found in user data');
            }
          } else {
            console.log('User document does not exist in Firestore');
          }
        }
      } catch (error) {
        console.error('Error fetching user data:', error);
      }
    };
    
    fetchUserData();
  }, []);

  return (
    <View style={styles.container}>
      <Text style={styles.text}>Hello, {userName}</Text>
    </View>
  );
};

const styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',
  },
  text: {
    fontSize: 20,
    fontWeight: 'bold',
  },
});

export default MainPage;

日志信息

LOG  current user UID is: 4sXptgVpAgUSh8jILHuv45R8fiz1
LOG  The doc is: {"_key": {"path": {"len": 2, "offset": 0, "segments": [Array]}}, "converter": null, "firestore": {"app": [FirebaseAppImpl], "databaseId": [DatabaseId], "settings": [FirestoreSettingsImpl]}, "type": "document"}   
LOG  User document: {"_converter": null, "_document": null, "_firestore": {"app": [FirebaseAppImpl], "databaseId": [DatabaseId], "settings": [FirestoreSettingsImpl]}, "_firestoreImpl": {"app": [FirebaseAppImpl], "databaseId": [DatabaseId], "settings": [FirestoreSettingsImpl]}, "_key": {"path": {"len": 2, "offset": 0, "segments": [Array]}}, "_userDataWriter": {"firestore": [Object]}, "metadata": {"fromCache": false, "hasPendingWrites": false}}
LOG  User Data: undefined
LOG  Name property not found in user data

已完成的排查步骤

  • 检查Firestore规则,确保允许基于用户UID的读取权限。
  • 通过控制台日志排查无法访问数据的原因。

问题分析与解决办法

从日志可见,userDocSnapshot.data()返回undefined,核心问题是文档实际不存在或权限配置有误,结合代码逻辑问题,可按以下步骤修复:

1. 修正文档存在判断逻辑

原代码中直接判断userDocSnapshot是否存在是错误的——即使目标文档不存在,getDoc仍会返回快照对象,只是其exists()方法会返回false。修正后的代码片段:

const userDocSnapshot = await getDoc(userDocRef);
console.log('User document exists:', userDocSnapshot.exists());

if (userDocSnapshot.exists()) {
  const userData = userDocSnapshot.data();
  if (userData && userData.name) {
    setUserName(userData.name);
    console.log('Name property found:', userData.name);
  } else {
    console.log('Name property not found in user data');
  }
} else {
  console.log('User document does not exist in Firestore');
}

2. 验证Firestore文档UID匹配性

确认Firestore中users集合下的文档ID,是否与日志输出的current user UID完全一致(注意大小写、特殊字符)。很多时候是创建用户文档时误用了其他标识(如邮箱)而非Auth的UID。

3. 重新检查Firestore规则

确保规则正确限制用户仅能读取自己的文档,示例规则:

rules_version = '2';
service cloud.firestore {
  match /databases/{database}/documents {
    match /users/{userId} {
      allow read, write: if request.auth != null && request.auth.uid == userId;
    }
  }
}

可临时将规则改为allow read, write: if true;测试,若能读取数据则说明原规则配置有误。

4. 添加Auth状态监听

auth.currentUser可能在组件挂载时未完成初始化,建议通过Auth状态监听确保用户完全登录后再获取数据:

useEffect(() => {
  const unsubscribe = auth.onAuthStateChanged(async (user) => {
    if (user) {
      const userDocRef = doc(db, 'users', user.uid);
      const userDocSnapshot = await getDoc(userDocRef);
      if (userDocSnapshot.exists()) {
        const userData = userDocSnapshot.data();
        userData.name && setUserName(userData.name);
      }
    }
  });

  return () => unsubscribe(); // 组件卸载时取消监听
}, []);

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.09 00:40:22