简体   繁体   中英

Unable to set State of React Component

I'm calling an API using the fetch API inside my react component to set the state. This is my code.

class MyComponent extends React.Component {

  constructor(props) {
    super(props);
    this.state = { fullName: null, uid: null };

  }
  componentWillMount(){

    fetch(url)
      .then(
        function(response) {
          if (response.status !== 200) {
            console.log('Looks like there was a problem. Status Code: ' +
              response.status);
            return;
          }

          response.json().then(function(data) {
            this.setState( fullName = data.first.givenName + " " + data.lastName,
              uid =data.uid );
          });
        }
      )
      .catch(function(err) {
        console.log('Fetch Error :-S', err);
      });
  }


  render() {
    return (
      <div className="header">
        <nav className="navbar navbar-default navbar-fixed-top">
          <div className="navbar-header">
            <a className="navbar-brand" href="#"> {this.state.fullName}</a>
          </div>


          <div className="brand-right">
            <ul className="nav navbar-nav navbar-right">
              <li><a href="#">UID: {this.state.yguid} </a></li>
            </ul>
          </div>
        </nav>
      </div>
    );
  }
}

export default MyComponent;

I get the following error:

Uncaught (in promise) TypeError: Cannot read property 'setState' of undefined

I can't seem to understand why setState is not working. If I console.log(data) inside the then block, it outputs the correct data, but then fails in the next line. How can I do this correctly.

The function you pass in then is not binded to current context, that cause this inside your callback function to be undefined rather than reference your component instance. Just use bind(this) to bind the callback with component like this:

.then(function () {
  // function body
}.bind(this));

or you can use arrow function, which binds the context implicitly:

.then(() => {
  // function body
});

This happens because this which you use under fetch is not same as the this under the class MyComponent .

Try to use arrow functions

fetch(url)
  .then((response) => {
    if (response.status !== 200) {
      console.log('Looks like there was a problem. Status Code: ' +
        response.status);
      return;
    }

    response.json().then((data) => {
      this.setState({
        fullName: data.first.givenName + " " + data.lastName,
        uid: data.uid,
      });
    });
  })
  .catch((err) => {
    console.log('Fetch Error :-S', err);
  });

Hope this helps!

The correct way to set a state is passing the state as an Object . Eg.:

this.setState({
  fullName: data.first.givenName + " " + data.lastName,
  uid: data.uid
});

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM