简体   繁体   中英

Why can't I set server's answer to state?

I'm trying to get JSON from api.openweathermap.org and set it to state, but as result I get console.log

What should I do set JSON's info to state.weather?

import React, { Component } from 'react';

class GetWeather extends Component {
    constructor(props) {
        super(props);
        this.state = {
            weather: {},
            temp: ''
        }
    };

        weather = async (e) => {
    e.preventDefault();
    try {
        let response = await fetch('http://api.openweathermap.org/data/2.5/weather?q=London,uk&APPID=b40640de9322c8facb1fcb9830e8b1f4');
        let data = await response.json();
        // if I will use response.text() here, than next console.log will show me the object literal that I got from server
        console.log('data: ' + data);
        await this.setState({weather: data});
        console.log('state ' + this)
    } catch (e) {
        console.log(e);
    }
}

    render() {
        return (
            <button onClick={this.weather} />
        )
    }
}

export default GetWeather;

React state updates are asynchronous and occur at the end of the function call (ie all set state calls are "collated" and processed together, part of the reconciliation), so console logging the state update immediately after doesn't work.

Try to use the setState callback

this.setState({weather: data}, () => console.log('state', this.state));

State will update and call the callback afterwards, synchronously, so you'll see the new state value. You also do not need to await it.

You cannot await setState. To execute code after your state has changed, setState actually has 2nd argument which is a callback function that is executed after the state has changed. Your code should look something like this:

console.log(data);
this.setState({weather: data}, () => {console.log(this.state)});

Here you can see another problem. Since you are concatenating a string ('data:') with an object, your object is converted to the string and you get [object Object]. To avoid this, print either only the object or print an object separately from the string like this: console.log('data:', data) . Note that I used a comma here, not a plus.

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