javascript - React - 在状态中写入和读取嵌套对象

标签 javascript reactjs firebase firebase-realtime-database state

我正在开发一个 React 应用,该应用从 Google Firebase 上的数据库中获取数据。

数据库的组织方式如下:

users {
    user 1 {
        name
        surname
        ... 
    }
    user 2 {
        name
        surname
        ...
    }
}

如何在 React 中检索数据:

我从 URL 中获取位置和工具来过滤搜索结果(目前仅使用位置,但想同时使用两者),并且我成功地在控制台中打印了对象。

componentWillMount(){
    const searchResults = FBAppDB.ref('users');

    let location = this.props.location;
    let instrument = this.props.instrument;

    let profiles = [];
    searchResults.orderByChild('location').equalTo(location).on('value', (snap) => {
        let users = snap.val();
        Object.keys(users).map((key) => {
            let user = users[key];
            console.log(user);
            profiles.push(user);
        });
    });

    // this.setState({users: profiles[0]});
}

对象的控制台输出:

Object {name: "Whatever", surname: "Surrname", ... }

我似乎失败的是将这些对象(可能不止一个)保存在状态中,这样当用户更改页面上的其他过滤器时我可以更新 View 。

我尝试 setState 实际用户,但状态结果为空,知道吗?

除了写入之外,从状态获取数据的最佳方法是什么?如何循环遍历状态中的对象?

谢谢

编辑

这就是我的渲染函数的样子:

render(){
    return(
        <Row>
            {
                Object.keys(this.state.users).map(function (key) {
                    var user = this.state.users[key];
                    return <SearchResult user={user} />
                })
            }
        </Row>
    );
}

我尝试直接打印this.state.users,但不起作用。因此我试图想出一个(无效的)解决方案。对于这里出现的任何菜鸟错误,我深表歉意。

最佳答案

I tried to setState the actual user but the state results empty, any idea?

这是因为您的数据库操作 searchResult异步,并且 JavaScript 不会让同步代码等待异步代码完成。

在您的代码中,如果启用带注释的 setState 调用,则该代码将在异步代码等待响应时执行。

您需要在其中setState:

searchResults.orderByChild('location').equalTo(location).on('value', (snap) => {
    let users = snap.val();
    const profiles = Object.keys(users).map((key) => users[key]);
    this.setState({ users: profiles[0] });
});

每当您希望在异步代码之后执行某些操作时,请将其放入 callback 中(到异步 fn)或使用 Promise .

<小时/>

What would be the best way to get the data back from the state? How do I loop through objects in the state?

setState 也可以是异步的。但您将在下次渲染时获得新的更新状态。因此,在 render() 中,您可以以 this.state.users 的形式访问状态中的 users 并使用它执行操作。

更新:

componentWillMount(){
    const searchResults = FBAppDB.ref('users');
    const location = this.props.location;
    const instrument = this.props.instrument;

    searchResults.orderByChild('location').equalTo(location).on('value', (snap) => {
        const users = snap.val();
        const profiles = Object.keys(users).map((key) => users[key]);

        // previously we were setting just profiles[0]; but I think you need 
        // the entire list of users as an array to render as search results
        this.setState({ users: profiles }); // set the whole data to state
    });
}


render(){
    const users = this.state.users || []; // note that this.state.users is an array

    return(
        <Row>
            {
              users.length > 0 
              ? users.map((user) => <SearchResult user={user} />)
              : null
            }
        </Row>
    );
}

关于javascript - React - 在状态中写入和读取嵌套对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40716051/

相关文章:

javascript - 无法在 firebase 实时数据库中存储新记录

javascript - 为什么这个 AngularJS 数据绑定(bind)不起作用?

javascript - ReactJS,如何从 onChange 下拉列表更改表单类型

javascript - 如何计算字符串集合的哈希码(0..5000 个元素)

html - 音频标签不适用于 React.js

reactjs - 在屏幕上显示图像之前触发事件?

node.js - Firebase - Node 云函数解析触发器时出错 : Cannot find module 'firebase-functions'

android - 前台的 Firebase 通知

javascript - jQuery .on() 不使用字符串变量作为键

javascript - 确定哪个框架(名称)调用了 JavaScript 中的函数