I’m passing all the functional tests for this project except one. I get an error
1) Functional Tests PUT /api/issues/{project} => text One field to update:
2:08
Uncaught Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client
I goggle the error and understand it a little but not enough to see what’s wrong. The other tests pass and my code for those tests looks the same as the one that fails. The failing one is for
test('One field to update',
suite('PUT /api/issues/{project} => text', function() {
test('No body', function(done) {
chai.request(server)
.put("/api/issues/test")
.send({_id: "kyPXsHr_z"})
.end( function (err, res) {
assert.equal(res.status, 200);
assert.equal(res.text, "no updated field sent");
done();
})});
test('One field to update', function(done) {
chai.request(server)
.put("/api/issues/test")
.send({_id: "hmv-iLuCv",
issue_title: "title 1"})
.end( function (err, res) {
assert.equal(res.status, 200);
assert.equal(res.text, "successfully updated");
done();
})});
test('Multiple fields to update', function(done) {
chai.request(server)
.put("/api/issues/test")
.send({_id: "kyPXsHr_z",
issue_title: "title",
issue_text: "text"})
.end( function (err, res) {
assert.equal(res.status, 200);
assert.equal(res.text, "successfully updated");
done();
})});
});
I’m just jumping in the middle here. Your error message isn’t saying that status is undefined. It is saying that res is undefined.
You need to guard yourself against errors, by first checking if err is defined, if it isn’t then you’ll also want to make sur res is defined such as
if (err) {
// Put whatever you want here to handle errors
} else if (res) {
// If there is no err, then you should be able to assume there is a res,
// but I always check just in case.
}
Hope this helps.
PS: Headers always have to be the first thing sent in an HTTP response and when you do, its like dropping an envelope in the post office, once you send headers, they are gone and cannot be modified.
@shadowfox476 thanks, that makes sense because when I rewrote the code I left out the first forward slash. Good tip on checking if (err).
So I’m back to having the original error message. I’ve read some more on it and I still don’t understand where the header is set and where it is trying to reset the header? The error message points to the line in my original post. I don’t see what is different in that test from the other tests to cause the error?
The problem must be somewhere in here
.put(function (req, res){
var project = req.body;
var id = project._id;
var updates = {
issue_title: project.issue_title,
issue_text: project.issue_text,
created_by: project.created_by,
assigned_to: project.assigned_to,
status_text: project.status_text,
open: project.open
};
if (!project.issue_title) { delete updates.issue_title}
if (!project.issue_text) { delete updates.issue_text}
if (!project.created_by) {delete updates.created_by}
if (!project.assigned_to) {delete updates.assigned_to}
if (!project.status_text) {delete updates.status_text}
if (!project.open) {delete updates.open}
if (Object.keys(updates).length === 0) {
res.send("no updated field sent");
} else {
updates.updated_on = new Date();
};
Issue.findOneAndUpdate({_id: id}, updates, {new: true}, function(err, doc) {
if (err) {
console.log(err);
} else if (!doc) {
res.send("could not update " + id)
} else {
console.log(doc);
res.send("successfully updated");
}
})
})
hi eoja
use return res.send()
because res alone do not stop execution of your code
even if the if statement is true you still execute the findOneAndUpdate function
@yakhousam thanks for the help! That does fix the problem because findOneAndUpdate was executing no matter what. Late last night I realized it had something to do with the if/else statements, so after trying your suggestion this morning I also put findOneAndUpdate within the else part of if/else statement so it only executes if there was an update field sent. So just moving one curly bracket further down the code worked also.