0

I keep getting this error message: Can't set headers after they are sent. I'm pretty new. This is a simple to-do list app that saves each item to mongodb, and displays each item on the page. It also has the ability to remove items. Everything seems to work okay, but I still keep getting this message. The error message occurs every time I try to use delete item route. Like I said, it works like I expect it to. It removes the item from the list, and from the database, but I still keep getting this error message. Here's what the delete route looks like:

app.delete('/:id', function(req, res){
    var removal = req.params.id;
    MongoClient.connect(dbUrl, function(err, db){
        var list = db.collection('list');
        list.remove({ _id: ObjectId(removal)}, updateList(res));
    });
    res.redirect('/');
});


//update list displayed on page -- to be used via callback after db change
function updateList(res){
    MongoClient.connect(dbUrl, function(err, db){
        var list = db.collection('list');
        list.find({}).toArray(function(err, docs){
            res.render('index', { title: 'To do:', list: docs });
        });
    });
};

I used res.redirect('/') to make it so the URL shown in the address bar doesn't show the ObjectId of each item I remove, but it seems like that might be the problem, because when I get rid of it, the error doesn't come up. But I don't want that ID number showing up at the top. Doing it this way seems to work. Why does it give me an error message? Is there another way to accomplish this?

Stennie
  • 63,885
  • 14
  • 149
  • 175
Nathan
  • 2,317
  • 3
  • 15
  • 18
  • 2
    possible duplicate of [How to return the response from an asynchronous call?](http://stackoverflow.com/questions/14220321/how-to-return-the-response-from-an-asynchronous-call) And you really need to read that to understand the various things you are doing wrong here. – Blakes Seven Jul 05 '15 at 08:25

2 Answers2

1

Probably this piece of code going to help you. But you need to learn more about callbacks, functions and how to use them...

app.delete('someRouteName/:id', function(req, res){
    var removal = req.params.id;
    MongoClient.connect(dbUrl, function(err, db){
        var list = db.collection('list');
        list.remove({ _id: ObjectId(removal)}, function(error){
            if(error){
                // Handle error
            }
            else{
                list.find({}).toArray(function(err, docs){
                    if(err){
                        // Handle error
                    }
                    else{
                        return  res.render('index', { title: 'To do:', list: docs });
                    }
                });
            }
        });
    });
});

~ Cheers

Soni Pandey
  • 514
  • 5
  • 16
  • Okay, that's basically a much cleaner version of the code that I have, and with error handlers, but it still does the exact same thing mine does if I remove the res.redirect('/'). There's still the problem I mentioned that I'm trying to make it so that the URL bar doesn't display the ObjectId, and that's why I'm using redirect. But redirect is what's giving me the error. Do you know if there's a better way to remove the ObjectId from the URL bar? EDIT: Figured it out. Just removed return from res.render, then returned res.redirect inside of a callback on res.render. – Nathan Jul 06 '15 at 12:24
0

You probably need to use return before res.redirect

return res.redirect('/');
Bidhan
  • 10,607
  • 3
  • 39
  • 50
  • Try moving `res.redirect('/');` right below `list.remove({ _id: ObjectId(removal)}, updateList(res));` – Bidhan Jul 05 '15 at 09:00