尝试从componentDidMount中的ajax调用中呈现状态值失败(React)

时间:2016-10-10 09:12:54

标签: javascript arrays ajax reactjs state

我在与Axios的React中进行了一次AJAX调用,我对如何处理响应感到有些困惑。

这是我的代码:

componentDidMount() {
   axios.get('https://jsonplaceholder.typicode.com/users')
      .then( res => {
         const users = res.data
         this.setState({ users });
      });
}

render() {
   console.log(this.state.users)  
   return (
   <div>
      {this.state.users.map( user => <p>{user.name}</p>)}
   </div>
   )
}

当我在console.log结果时,会返回两个值:

  1. [] - 分配给初始状态的空数组
  2. 来自API的预期数组。
  3. 这可以解释为初始化时返回的状态值,然后是componentDidMount。

    我的问题出现在我如何访问this.state.users值。显然,无论何时访问它,我都希望从AJAX响应中返回值,但是,例如,我尝试从数组中的第一个对象渲染name属性...

    {this.state.users[0].name}

    ...它试图访问[],因此不返回任何内容。

    但是,如果我尝试遍历数组元素......

    {users.map( user => <p>user.name</p> )}

    ...它按预期返回值。

    我不知道为什么它适用于第二个例子而不是第一个例子。当然,如果第一个尝试从初始状态值(空数组)中提取数据,那么当映射this.state.users时,它也会尝试映射空数组并且不返回任何内容或者是错误。

    我显然没有完全理解这里的React渲染过程以及componentDidMount在组件生命周期中的工作方式。我试图将响应值直接分配给状态是错误的吗?

    如果有人能帮忙解决这个问题,我们将不胜感激。

2 个答案:

答案 0 :(得分:2)

最初在map()上使用this.state.users时,它会在空数组(不会呈现任何内容)上执行此操作。一旦响应到达,并且this.setState({ users })被调用,render()将再次运行。这次,用户数组不再为空,并且将对阵列中的每个用户执行map()操作。

但是,当您最初在空数组上使用{this.state.users[0].name}时,您正在尝试访问尚不存在的对象的name属性 - 这将导致错误。为了防止错误,您可以在访问对象的属性之前进行检查:

{this.state.users.length > 0 && this.state.users[0].name}

现在它的行为与第一个示例相同。即由于render(),第一个this.state.users.length = 0实际上不会做任何事情。但是,只要新用户调用this.setState()render()就会再次运行,而这次this.state.users[0].name可用。

答案 1 :(得分:0)

构造函数还有另一种方法。只需将您的状态添加为空数组用户 -

   constructor(props) {
      super(props);
      this.state = {
         users: []
      };
   }

首先使用空用户数组渲染此组件。当您触发状态更新时,使用新数组重新组件。