[英]How do I prevent a function from being run before data is loaded into this.state (i.e. in componentDidMount)?
我有一个函数getRepresentativeName()
它使用来自this.state
的一段数据( this.state.communityData.Representative
)来索引到数据库并检索一个字符串。 我的意图是,当组件安装时, this.state
所有信息,包括this.state.communityData.Representative
,都将被填充,并且代表的名字将出现在由{...}设置的位置。 但是,该函数在调用第一次渲染时立即运行,不会等待组件挂载; 作为一个结果,因为this.state
未填充然而,getRepresentativeName功能崩溃。
我放了一个三元语句来检查communityData JSON对象是否被填充(逻辑是如果没有填充,即==={},只返回null
而不是executing getRepresenativeName())
; 有趣的是,网页崩溃不管(有相同的问题: getRepresenativeName()
之前被称为this.state
中填充componentDidMount()
有人可以向我解释为什么会发生这种情况,以及如何在不向this.state
添加冗余数据的情况下解决这种情况? 我不确定这是否是解决它的方法,但我认为如果有一种方法可以让getRepresentativeName()
函数等到componentDidMount()
完成,则可以解决问题。 谢谢!
注意:如果我不调用该函数而只是将{...}替换为{ this.state.communityData.Representative} ,这会使用代表 ID 而非名称填充元素,页面呈现完美。 此外,我尝试将getRepresentative
name getRepresentative
回调,但仍然无效(即页面在尝试呈现时仍然崩溃)。
async getRepresentativeName() {
const representativeSnapshot = await database()
.ref('users')
.child(this.state.communityData.Representative)
.child('name')
.once('value');
return representativeSnapshot.val();
};
render() {
console.log('starting render');
return (
<View style={styles.containerScreen} testID="communityScreen">
{/*
This the container that holds the community Image
and its description,
*/}
<View style={styles.containerhorizontal}>
<View style={styles.containervertical}>
<Image
source={require('../../sample_images/va10.jpg')}
style={styles.image}
/>
</View>
<View style={styles.containervertical}>
<Text style={styles.containerhorizontal}>
Description: {this.state.communityData.Description}
</Text>
<Text style={styles.containerhorizontal}>
Representative: **{this.state.communityData !== {} ?this.getRepresentativeName() : null}**
</Text>
...
这里的典型模式是使用某种加载属性初始化您的状态。 然后,根据来自用户界面的输入异步加载数据。 该输入可能来自用户,也可能来自生命周期事件。 在这种情况下,componentDidMount。 您的组件应该知道如何在加载为真和数据可用时进行渲染。
class MyComponent extends React.Component {
state = {loading: true, error: null, representative: null}
componentDidMount() {
fetchData().then((representative) => {
this.setState({ loading: false, representative })
}).catch((error) => {
this.setState({ loading: false, error: error.message })
})
}
render() {
return this.state.error
? <span>woops</span>
: this.state.loading
? <span>busy</span>
: <div>Representative: {this.state.representative.name}</div>
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.