0

It's a continuation of question from here . My aim is to update all the documents with minimum score.

var MongoClient=require('mongodb').MongoClient;
var server=require('mongodb').Server;

var mongoclient=new MongoClient(new server("localhost",27017));

mongoclient.connect("mongodb://localhost:27017/school",function(err,db){

var db=mongoclient.db('school');
cursor=db.collection('students').aggregate(
[
  {$match : {"scores.type" : "homework"}},
  {$unwind:"$scores"},
  {$group : {_id : '$name','minimum' : { $min :"$scores.score"  }}}
], function(err, result) {   // callback
        console.dir(result);
    }
);
cursor.each(function(err,doc)
{
db.collection('students').update({'_id':doc._id},{$pull:{'scores':{'score':doc.minimum}}});
});
});

Using this i am getting error

node app.js 
undefined

/home/oroborus/node_modules/mongodb/lib/mongodb/mongo_client.js:475
          throw err
                ^

TypeError: Cannot call method 'each' of undefined
        at /home/oroborus/hw3-1/app.js:18:8
        at /home/oroborus/node_modules/mongodb/lib/mongodb/mongo_client.js:83:5
        at /home/oroborus/node_modules/mongodb/lib/mongodb/mongo_client.js:472:11
        at process._tickCallback (node.js:415:13)

According to previous programs written by me and the post above this looks correct then still why does this error persists ?
[Edit]
When i did console.dir(cursor) it said undefined. Why ? This might be because of the asynchronous behaviour of Node.js but how do i rectify it. How do i make it synchronous.
Thanks

0

1 Answer 1

0

collection.aggregate() is asynchronous, aggregate won't return a cursor until it's done, which is in its callback. I don't think aggregate() actually returns a cursor. The result should be in 'result' of the callback, but if it does and if you need to iterate through it, the code should be in its callback:

var MongoClient=require('mongodb').MongoClient;
var server=require('mongodb').Server;

var mongoclient=new MongoClient(new server("localhost",27017));

mongoclient.connect("mongodb://localhost:27017/school",function(err,db){
  cursor=db.collection('students').aggregate(
    [
        {$match : {"scores.type" : "homework"}},
        {$unwind:"$scores"},
        {$group : {_id : '$name','minimum' : { $min :"$scores.score"  }}}
    ], function(err, result) {   // callback
        console.dir(result);

        if (cursor) {
            cursor.each(function(err,doc)
            {
                db.collection('students').update({'_id':doc._id},{$pull:{'scores':{'score':doc.minimum}}});
            });     
        }


    }
  );
});

Update: Just read the document and aggregate() doesn't return a cursor (unless it's 2.6 or greater, option can be specified to return cursor): http://mongodb.github.io/node-mongodb-native/api-generated/collection.html

Sign up to request clarification or add additional context in comments.

3 Comments

have a look here
it looks like you can get the cursor on 2.6+. we have all node server on openshift and openshift is using mongodb 2.4, so I didn't know about that... Thanks for the link Saras...
i am using 2.6.9 i cursor.on function is working for me but the normal method to update data won't work i guess. I need how to update.. I am not able to find that :(

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.