【问题标题】:Rendering React components mapped from Firebase Firestore渲染从 Firebase Firestore 映射的 React 组件
【发布时间】:2019-05-20 12:33:40
【问题描述】:

我已经花了几天的时间试图解决这个问题,希望大家能帮助我。我想从 Cloud Firestore 数据库中获取帖子并将其显示在 React 应用上。

我在 Firestore 中的数据结构如下:

[项目]/NewsPosts/[文档]

每个文档在 Firestore 中的结构如下:

[随机生成的id]

  • 标题:[字符串]
  • 正文:[字符串]

我通过执行以下操作获得了帖子:

let posts= [];

//db = firebase.firestore();

db.collections.("NewsPosts").get().then((snapshot) => (
  snapshot.forEach((doc) => (
    posts.push({
      id: doc.id,
      title: doc.data().title,
      body: doc.data().body
    })
  ))
));

这成功地创建了一个包含我想要的信息的对象数组,因此获取数据不是问题。然而,当我去映射这个数组来创建帖子时,什么都没有被创建。我已经尝试了映射数组的所有变体来创建组件,但它不起作用。

但是,当我对一组对象进行硬编码并映射该对象时,它就可以工作了。例如,这适用于硬编码的对象数组:

//hard is the hardcoded array
let displayPosts = hard.map((p) => (
    <div key={p.id}>
        <h1>{p.title}</h1>
        <p>{p.body}</p>
    </div>
))

return(
    <Page>
        {displayPosts}
    </Page>
);

当我在浏览器控制台中比较硬编码数组和其他数组时,数组看起来不同。

我想是数组中的这种差异导致了问题。

如果有 2 个元素,这就是它们在浏览器控制台中的外观:

(2)[{...},{...}]      (hardcoded)
[]                    (array filled from firestore)

但是,关于数组的其他所有内容在浏览器控制台中都是相同的。

为什么这些数组看起来不同?这是让我无法正确映射每个索引处的对象的原因吗?如何让映射作用于从 Firestore 获取的对象数组?

提前感谢您的帮助!这让我很头疼。

【问题讨论】:

  • 你能告诉鳕鱼在哪里尝试映射数组吗?
  • 当然!我编辑了我的原始帖子以添加它

标签: javascript arrays reactjs firebase google-cloud-firestore


【解决方案1】:

我已经解决了!

我并没有一成不变地改变它。

这使它正常工作:

constructor(props){
    super(props);

    this.state = {
        posts: []
    }
}

componentDidMount = () => {
    db.collection("NewsPosts").get().then((snapshot) => (
        snapshot.forEach((doc) => (
            this.setState((prevState) => ({
                posts: [...prevState.posts, {
                    postID: doc.id,
                    title: doc.data().title,
                    body: doc.data().body,
                    featured: doc.data().featured
                }]
            }))
        ))
    ))
}

【讨论】:

  • 我已经多次遇到这个问题,并不断回到这个答案。总是修复它!
【解决方案2】:

您对问题的回答仍然缺少正确的键。因此,Mango 问题的完整答案(以及自己的答案)将是:

class Sample extends React.Component {

constructor(props){
  super(props);

  this.state = {
    posts: []
  }
}

componentDidMount = () => {
    db.collection("NewsPosts").get().then((snapshot) => (
        snapshot.forEach((doc) => (
            this.setState((prevState) => ({
                posts: [...prevState.posts, {
                    postID: doc.id,
                    title: doc.data().title,
                    body: doc.data().body,
                    featured: doc.data().featured
                }]
            }))
        ))
    ))
}

    render() {
        let displayPosts = this.state.posts.map((p) => (
            <div key={p.postID}>
                <h1>{p.title}</h1>
                <p>{p.body}</p>
            </div>
        ))

        return(
            <Page>
                {displayPosts}
            </Page>
        );
    }

}

【讨论】:

    【解决方案3】:

    根据我对您问题的理解,我认为以下代码应该可以帮助您解决问题。

    class Sample extends React.Component {
    
        state = {
            posts: []
        }
    
        componentDidMount() {
            let posts = [];
            db.collections.("NewsPosts").get().then((snapshot) => (
                snapshot.forEach((doc) => (
                    posts.push({
                        id: doc.id,
                        title: doc.data().title,
                        body: doc.data().body
                    })
                ))
                this.setState({ posts })
            ));
        }
    
        render() {
            let displayPosts = this.state.posts.map((p) => (
                <div key={p.id}>
                    <h1>{p.title}</h1>
                    <p>{p.body}</p>
                </div>
            ))
    
            return(
                <Page>
                    {displayPosts}
                </Page>
            );
        }
    
    }
    

    这段代码强调的要点是,react 是数据驱动的。本质上,您有一个名为 posts 的状态数组,您将映射到该数组以呈现您的数据。当这个数组为空时,就像在初始渲染时获取数据之前的情况一样,不会渲染任何项目。一旦数据从数据库返回,数据就会添加到您的帖子数组中。调用setState 方法来强制进行新的渲染,但这次我们有数据要显示。

    如果此答案表明我误解了您的问题,请继续跟进。

    希望这会有所帮助!

    【讨论】:

    • 感谢您的回答!不幸的是,这不起作用。什么都没有显示。我不确定这些帖子是否会被添加到数组中,但我稍后必须对其进行测试。
    猜你喜欢
    • 2021-02-22
    • 2021-04-22
    • 2019-10-20
    • 2018-12-01
    • 2014-10-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-04
    相关资源
    最近更新 更多