I am using .fetch()
to fetch data from an API, I used .then()
if the data is successfully fetched and .catch()
of there are error. Here is the following code:
let data;
await fetch(API + "/demo/demo", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: body,
})
.then(async (result) => {
data = await result.json();
})
.catch((error) => {
return res.status(500).render("errors/500", {
document: "Error",
message: error.message,
});
});
if (!data) {
return res.status(500).render("errors/500", {
document: "Error",
message: "No Data",
});
}
Explanation:
The let data
is created as a placeholder, it will be completed when the .then()
is finished, .catch((error))
is used when .fetch(API)
has any errors. if(!data)
is used when there is no data and it will return an error.
"Cannot set headers after they are sent to the client" happens because .catch()
already return response but also if(!data)
also return the response.
What I tried:
I think the problem is that I send the "same" response twice. Because .catch()
send the response and then if(!data)
also send the same response again.
I've "fixed" it by removing .catch()
or assign error.message
without performing a return.
But, I was expecting that the .catch()
will return the response only because I have place return
in front of it and the return response at if(!data)
will not be executed.
I am hoping for an explanation or suggestions
You get the error because 'catch' is asynchronous and you send a response to the client twice.
Here is what happens when you run the code:
1- You make a fetch request.
2- Since fetch request is not completed, data is still undefined. You send a response to the client with an error.
3- Fetch is resolved, and if there are any errors with fetch request, you try to send another error message to the client within the same response which causes the error.
Catch will only catch any errors with the api request, it will not catch the errors happening within itself.
You can check whether the data exists inside the then clause like this:
await fetch(API + "/demo/demo", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: body,
})
.then(async (result) => {
const data = await result.json();
// Also make sure that data is not an empty object
if (!data) {
return res.status(500).render("errors/500", {
document: "Error",
message: "No Data",
});}
})
.catch((error) => {
return res.status(500).render("errors/500", {
document: "Error",
message: error.message,
});
});