反应。为什么this.state没有正确更新?

时间:2018-04-11 12:20:10

标签: javascript reactjs promise axios

所以,我尝试按条件运行该函数:如果我在catch方法中遇到错误。

为此,我在组件状态中实现this.state.loginError,如果出现错误,将在true上更改。所以,在error之后 - this.state.loginError回复true(这也是我在console.log中看到的),但在状态更改后 - 我的函数loginError(target)执行了不管怎么说都不想开始。

请参阅下面的代码和日志:

class LoginPage extends Component {
    constructor(props) {
        super(props);
        this.state = {
            navigate: false,
            loginError: false,
        }
    }

    handleSubmit = (e) => {
        e.preventDefault();

        axios.post('http://localhost:3016/auth/login', userLogin, {withCredentials: true})
            .catch(err => {
                    this.setState({
                        loginError: true
                    });
                    console.log(this.state.loginError);  // gives `true`
            });

            if (this.state.loginError) {
                console.log('Error!') //does not work
                loginError(target);
            }
    };

4 个答案:

答案 0 :(得分:1)

因为axios.post是asyc函数,并且首先触发if条件,然后.catch挂钩。要解决此问题,请尝试在其他位置替换您的条件,例如componentDidUpdate method

componentDidUpdate() {
 if (this.state.loginError) {
    console.log('Error!') //does not work
    loginError(target);
    this.setState({ loginError: false });
   }
}

答案 1 :(得分:1)

请检查:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/async_functio

你基本上是在没有捕获错误时检查状态,因此状态没有改变。

如果将代码移动到渲染方法,您将看到它将起作用,因为它将在状态更改后重新渲染。或者您使用componentDidUpdate方法进行状态更改。

答案 2 :(得分:0)

为什么不尝试使用Promise,这是一种非常清晰简单的方法。

class LoginPage extends Component {
    constructor(props) {
        super(props);
        this.state = {
            navigate: false,
            loginError: false,
        }
    }

    handleSubmit = (e) => {
        e.preventDefault();
        return new Promise(resolve, reject){
        axios.post('http://localhost:3016/auth/login', userLogin, {withCredentials: true})
            .catch(err => {
                    reject(err);
            })
            .then(result => resolve(result));
        }

        //Else where in Your component use this promise, where ever you call it..

        handleSubmit().then(// success code).error(// error code)
    };

答案 3 :(得分:0)

由于axios.post会返回一个承诺,因此您在其之后编写的所有代码都将在.then().catch()语句之前执行。如果您需要在请求失败时调用loginError()函数,可以在.catch语句中调用它:

axios.post('http://localhost:3016/auth/login', userLogin, {withCredentials: true})
    .catch(err => {
         loginError(target);
    });

如果在更新状态后需要执行函数,可以使用setState回调(第二个参数):

axios.post('http://localhost:3016/auth/login', userLogin, {withCredentials: true})
    .catch(err => {
         this.setState({ loginError: true }, () => { loginError(target); })
    });
相关问题