简体   繁体   中英

setState not firing inside axios POST request error handler

I am trying to set up an error handler for a React Component SignupForm.js that is responsible for registering users. In particular, the handler I am focused on implementing involves handling instances of a supplied user email already in use.

Here is my POST request:

await axios
            .post("http://localhost:8000/signup", {
                name,
                email,
                password,
                tokenValue,
            })
            .catch((error) => {
                console.log("ERROR --> ", error);
                //this.displayError(error);
                this.setState(
                    {
                        err: true,
                        errcode: error.response.data.errcode,
                        errtext: error.response.data.errText,
                    },
                    () => {
                        console.log("setstate done");
                    }
                );
            })
            .then((res) => {
                if (res !== undefined) {
                    console.log(res.data);
                }
            });

The image below shows Chrome Dev Tools output:

打印出捕获的错误对象。

As you can see, console.log("Error --> ", error); is indeed firing. However, this.setState() doesn't seem to be firing. There are a few indications of this.

  1. The SignupForm state, as observed using the React DevTools plugin, remains unchanged.
  2. I have included a print statement at the very top of my render() function like so:
render() {
        console.log(this.state);
        return (
            <div className="form-container">
                <form
                    name="sign-up"
                    method="post"
                    className="form-sign-up"

despite the notion that setState() calls are supposed to trigger re-renders, the component state never gets printed to the console after the error being caught.

  1. console.log("setstate done"); never fires, as the output is also missing from the DevTools console.

Things I have tried

  1. I tried encapsulating the setState() call into a error handler function displayError(e) , like so:
displayError = (e) => {
        this.setState(() => ({
            err: true,
            errcode: e.response.data.errcode,
            errtext: e.response.data.errText,
        }));
    };

This didn't seem to have any effect. I also tried calling displayError(e) after having called this.displayError = this.displayError.bind(this); in the component constructor, which similarly had no effect.

At this point, I'm not really sure what else to try.

Figured it out. Initially, I was quite set on trying to get my code posted online for you folks to take a look at. After getting to know CodeSandbox a bit, I thought I was going to need to learn Docker so I could compose the front-end and back-end while having a free MySQL DB hosted somewhere online.

This was discouraging to me, as I knew Docker might take a bit of time to learn and I wanted to get to the bottom of this with the least amount of hoops possible.

I took what @S.Marx said and I investigated. After thinking about what they said a little more, it seemed strange to me as well that I would put my catch block before my then block.

Sure enough, swapping those two blocks completely solved the issue. The state is now being changed with the following:

await axios
            .post("http://localhost:8000/signup", {
                name,
                email,
                password,
                tokenValue,
            })
            .then((res) => {
                if (res !== undefined) {
                    console.log(res.data);
                    console.log("Signup Successful!!");
                }
            })
            .catch((error) => {
                console.log("Signup Error! --> ", error);
                //this.displayError(error);
                this.setState(
                    {
                        err: true,
                        errcode: error.response.data.errcode,
                        errtext: error.response.data.errText,
                    },
                    () => {
                        console.log("setstate done");
                    }
                );
            });

Of course, now the component that is supposed to render the state change on-screen isn't showing the error message. That, however, is a separate issue.

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