首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >打开数组时,未定义的Firebase不是对象

打开数组时,未定义的Firebase不是对象
EN

Stack Overflow用户
提问于 2021-06-26 15:09:03
回答 2查看 43关注 0票数 1

所以这真的很奇怪

这是我的代码,当它工作时

代码语言:javascript
运行
复制
useEffect(() => {
        // Alleen preview
           async function getTracksData() {
                let TrackData = await firebase
                    .firestore()
                    .collection('TrackScreen')
                    .doc('LeerjarenData')
                    .get();
                if (!TrackData.exists) {
                    console.log('Geen data')
                } else {
                    let TrackDatav2 = TrackData.data();
                    setTrackScreenData(TrackDatav2) 
                }
           } getTracksData()
            // SNAPSHOT USER DATA
            db.collection("users").doc(currentUserUID)
                .onSnapshot((doc) => {
                    setUserData(doc.data());
                });
    }, [])

    console.log(trackscreenData.data)

这很好用,但是当我把我的控制台改为

代码语言:javascript
运行
复制
console.log(trackscreenData.data[0]

它给出了这个错误

代码语言:javascript
运行
复制
TypeError: undefined is not an object (evaluating 'trackscreenData.data[0]')

然后当我再次将我的控制台更改为

代码语言:javascript
运行
复制
console.log(trackscreenData.data)

它起作用了,当我改变的时候,我又回到

代码语言:javascript
运行
复制
console.log(trackscreenData.data[0])

并保存为我提供所需数据的更改

我做错了什么?

EN

回答 2

Stack Overflow用户

发布于 2021-06-26 15:55:41

简而言之,在异步调用数据准备就绪之前,您正在尝试使用这些数据。

要处理数据尚未完成加载的情况,您应该使用:

代码语言:javascript
运行
复制
console.log(trackscreenData && trackscreenData.data)

根据代码中的模式,在组件的顶部有以下几行代码。

代码语言:javascript
运行
复制
const { currentUserID } = useAuth(); // or similar

const [userData, setUserData] = useState();

const [trackscreenData, setTrackScreenData] = useState();
// NOTE: check for typos: "trackscreenData" !== "trackScreenData"

在代码的第一次呈现时,trackscreenData将为undefined,因为您还没有将初始状态传递给useState()方法。

代码语言:javascript
运行
复制
const [trackscreenData, setTrackScreenData] = useState(/* initial state */);
代码语言:javascript
运行
复制
// `trackscreenData` initially set to `null`
const [trackscreenData, getTracksData] = useState(null);

// `trackscreenData` initially set to `[]`
const [trackscreenData, getTracksData] = useState([]);

// `trackscreenData` initially set to the result of the function,
// an array containing the elements 0 through 99. The function is
// only executed once to set the first value.
// trackscreenData = [0, 1, 2, 3, ... , 97, 98, 99];
const [trackscreenData, getTracksData] = useState(() => {
  Array.from({length: 100})
    .map((_, i) => i);
}

当React执行您的代码时,任何从useState调用(例如setTrackScreenData)返回的对setter的调用都是queued。只有当您的代码执行完毕后,才会对它们进行评估并触发任何新的呈现。

代码语言:javascript
运行
复制
const [count, setCount] = useState(0); // `count` is initially set to `0`

useEffect(() => {
  if (count < 10) {
    setCount(count + 1);
  }
})

console.log(count);

console.log("rendered");

// Console logs:
// > "0"
// > "rendered"
// > "1"
// > "rendered"
// > ...
// > "9"
// > "rendered"
// > "10"
// > "rendered"

用户数据的获取应该在它自己的useEffect调用中,并且应该返回它的取消订阅函数:

代码语言:javascript
运行
复制
useEffect(() => {
  if (!currentUserUID) {
    setUserData(null); // user not signed in
    return;
  }

  // SNAPSHOT USER DATA
  return db.collection("users") // <- note the return here
    .doc(currentUserUID)
    .onSnapshot((doc) => {
      setUserData(doc.data());
    });
}, [currentUserUID]);
代码语言:javascript
运行
复制
useEffect(() => {
  let disposed = false;

  // Alleen preview
  async function getTracksData() {
    let TrackData = await firebase
      .firestore()
      .collection('TrackScreen')
      .doc('LeerjarenData')
      .get();

    if (disposed) return; // component was removed, do nothing

    if (!TrackData.exists) {
      console.log('Geen data')
    } else {
      let TrackDatav2 = TrackData.data();
      setTrackScreenData(TrackDatav2) 
    }
  }

  getTracksData()
    .catch((err) => console.error(err)); // don't forget to handle errors!

  return () => disposed = true; // ignore result if component disposed
}, []);
票数 1
EN

Stack Overflow用户

发布于 2021-06-26 15:29:36

您正在通过.doc(...)指定文档ID,因此您将获得一个DataSnapshot作为响应,它不是一个数组。

如果你使用像.where(...)这样的查询,那么它将返回一个QuerySnapshot

QuerySnapshot包含零个或多个表示查询结果的DocumentSnapshot对象。可以通过docs属性将文档作为数组访问,也可以使用forEach方法枚举文档。文档的数量可以通过empty和size属性确定。

因此,如果只以这种方式获取单个文档,则不需要通过[0]访问文档,因为它不是一个数组。您可以简单地通过dataSnapshot.data()访问数据

虽然我看不到trackscreenData是在哪里定义的?

代码语言:javascript
运行
复制
useEffect(() => {
        // Alleen preview
           async function getTracksData() {
                let TrackData = await firebase
                    .firestore()
                    .collection('TrackScreen')
                    .doc('LeerjarenData')
                    .get();
                if (!TrackData.exists) {
                    console.log('Geen data')
                } else {
                    let TrackDatav2 = TrackData.data();
                    setTrackScreenData(TrackDatav2) 
                    console.log(trackScreenData)
                }
           } 
    }, [])
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/68140057

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档