简体   繁体   中英

“Cannot set headers after they are sent to the client” error after post request

need help with some weird error

this is express, nodejs service that hosted on heroku

this is my route controller code

async function PopupConroller(req, res) {


        let credential = req.credential;
        let zoho_token = null;
        console.log('res :>> ', res);
        try {
            zoho_token  = await axios.post(`https://accounts.zoho.com/oauth/v2/token?client_id=${credential.client_id}&client_secret=${credential.client_secret}&refresh_token=${credential.refresh_token}&grant_type=refresh_token`);
            console.log('zoho_token.data :>> ', zoho_token.data);

        } catch (error) {
            console.log('ex 2 :>> ',error);
        }
        console.log('res :>> ', res);


       res.status(200).json({status:"ok"});

       return;

}

when service received request, code throws this error (no error from axios.post request)

the response back: 200 OK with no body

Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client
 at ServerResponse.setHeader (_http_outgoing.js:530:11)
 at ServerResponse.header (/app/node_modules/express/lib/response.js:771:10)
 at ServerResponse.json (/app/node_modules/express/lib/response.js:264:10)
 at PopupConroller (/app/voicenter.js:261:28)
 at processTicksAndRejections (internal/process/task_queues.js:97:5)

when removing those lines everything is ok response: 200 OK with {status:"ok"}

async function PopupConroller(req, res) {


        let credential = req.credential;
        let zoho_token = null;
        console.log('res1 :>> ', res);
        try {
            //zoho_token  = await axios.post(`https://accounts.zoho.com/oauth/v2/token?client_id=${credential.client_id}&client_secret=${credential.client_secret}&refresh_token=${credential.refresh_token}&grant_type=refresh_token`);
            //console.log('zoho_token.data :>> ', zoho_token.data);

        } catch (error) {
            console.log('ex 2 :>> ',error);
        }
        console.log('res2 :>> ', res);


       res.status(200).json({status:"ok"});

       return;

}

in the first example,
When I checked the res object (console.log res1) the headers not sent, but in the second (console.log res2) I noticed that the response headers sent back.

WAY THIS LINE SENT THE HEADERS??? * need to say that similar code in other routes work prefect

zoho_token  = await axios.post(`https://accounts.zoho.com/oauth/v2/token?client_id=${credential.client_id}&client_secret=${credential.client_secret}&refresh_token=${credential.refresh_token}&grant_type=refresh_token`);

appreciate the help... thanks

I am just guessing here, is that what you want?

To expand on the snippet code below, you get the error cannot set headers after they are sent to the client because axios.post() is making the HTTP post request.

In your code, you make an HTTP call via axios so the headers get sent out.

After that, the JS parser continues the evaluation of the code and after the try block, because there is no error, it evaluates the res.status() for a response that has been already sent, hence the error.

So, to solve this issue, you can handle the post request as you do, without resending the response again to the client. You can then "do something" with the promise response within the ´thenable´ function.

If you want to post an optional object via axios, you can do this by passing the argument into the post request.

async function PopupConroller(req, res) {

        let credential = req.credential;
        let zoho_token = await axios.post("whatever", {"cat": "meaows"})
        .then((response)=> {
            // do something with the response
        })
        .catch((err) => console.log(err))
  
}

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