In the following post request, I have to save a list of contacts once save is completed find query has to be fired
router.route('/uploadContacts')
.post(function(req,res){
for(var i = 0; i < req.body.vishReqBody.Contacts.length; i++) {
contactNumberList.push(req.body.vishReqBody.Contacts[i].PhNo)
}
//find and save the contact details
ProfileDetails.findOne({ 'PhNo' : {$in:contactNumberList}} ,
function(err, profileDetail) {
req.body.vishReqBody.Contacts.find(
function(contact){
if(profileDetail&&profileDetail.PhNo&&contact&&contact.PhNo){
if(profileDetail.PhNo==contact.PhNo){
var contactsDetails = new contacts();
contactsDetails.PhNo=contact.PhNo
contactsDetails.RegStatus=profileDetail.Reg_Status
contactsDetails.profileId=profileDetail.Profile_Id
contactsDetails.PhoneBookName=contact.Name
contactsDetails.updatedByProfileId=req.body.vishReqHeader.AppId
contactsDetails.save(function(err,result){
logger.info("contacts saved");
})
}
}
else{
var contactsDetails = new contacts();
contactsDetails.PhNo=contact.PhNo
contactsDetails.RegStatus=0
contactsDetails.PhoneBookName=contact.Name
contactsDetails.updatedByProfileId=req.body.vishReqHeader.AppId
contactsDetails.save(function(err,result){
logger.info("inside else");
logger.info("contacts saved");
})
}
})
});
//once after save this part has to be fired to send the response
contacts.aggregate(
[
{
$lookup:
{
from: "ProfileDetails",
localField: "PhNo",
foreignField: "PhNo",
as: "Profile_Details"
}
},
{$match:{
$and: [
{PhNo: {$in: contactNumberList}}
]
}}
],
function (err, result) {
if(result){
res.send({
"result": {
"vishResHeader": {
"ReqNo": req.body.vishReqHeader.reqNo,
"ProcStatus": 0,
"ErrCode": 0,
"ErrMsgUsr": ""
},
"vishResBody": {
"Contacts": result
},
"vishResTrailer": {
"Authentication": ""
}
}
})
}
})
});
But before the save quire completes the query is fired and returns a incorrect response not sure how to wait until the save operation is completed and later to fire the find query
Note: find query has to be fired only after save
please suggest a way to accomplish it
Request body for reference
{
"vishReqHeader": {
"ClientId": "0",
"AppId": "100",
"ApiCode": "1007",
"ReqNo": "123456789"
},
"vishReqBody": {
"RegPhNo": "9880889660",
"Cnt": "3",
"Contacts": [{
"PhNo": "7777777777",
"Name": "Alex"
},
{
"PhNo": "9999999999",
"Name": "Cindy"
},
{
"PhNo": "8888888888",
"Name": "Rob"
}
]
},
"vishReqTrailer": {
"DeviceData": "lat=12.9677992|lng=77.596204|IMEI=1234567890|appVer=3.0.1|OS=ANDROID|SoftVer=6.0.1",
"Authentication": "securitytoken"
}
}
You should use q or async package. Which helps your nodejs code to run serially. I have implemented with q, I hope you can relate with this :
var InsertUser = function(fname, lname, email, password){
var deferred = q.defer();
var user = new Users();
user.email = email;
user.password = password;
user.emailVerified = false;
user.fname = fname;
user.lname = lname;
user.createdDate = new Date();
user.updatedDate = new Date();
user.save(function(new_user_err, new_user){
if(new_user_err){
deferred.reject(new_user_err);
}else{
deferred.resolve(new_user);
}
});
return deferred.promise;
}
And routes to call this function :
router.post('/RegisterUser', function(req, res){
var email = req.body.email;
var fname = req.body.fname;
var lname = req.body.lname;
var password = req.body.password;
InsertUser(fname, lname, email, password).then(function(user_data){
console.log(user_data);
console.log("User registered successfully");
res.json({result : 1})
}, function(user_error){
console.log(user_error);
res.json({ error : user_error });
});
});
So you can do the same wit your code. Make a separate function for ProfileDetails.findOne and save() which returns a promise and then fire query contacts.aggregate()