繁体   English   中英

NodeJs Mongoose循环收集数据

[英]NodeJs Mongoose collecting data in loop

希望对您有所帮助。

我有类似此架构的文档收集任务。

Task = { 
     title:'taskName', 
     performers:[ {userId:1,price:230}, {userId:2,price:260} ]
}   
Profiles = { id:1, name: 'Alex', surname: 'Robinson', etc.. }

最后,我应该收集所有数据,并作为响应返回配置文件对象数组。 问题是for循环在每个元素的所有.findOne()完成之前结束,并且返回空数组。 这是代码形式的获取。

代码在这里:

apiRoutes.get('/performers/:id', function(req,res,next){

var profArr = []; 
Task.findOne({'_id':req.params.id},function(err, doc){
  for(var i = 0; i<doc.performers.length; i++){
    var profile = {
      price: 0,
      name: '',
      surname: ''         
    };
    profile.price = doc.performers[i].price;
    Profile.findOne({'_id':doc.performers[i].userId},function(err,doc){
      if (err) throw err;
      profile.name = doc.name;
      profile.surname = doc.surname;          
      profArr.push(profile);
    });
  }
  return res.json({success:true,
                   message:'Performers data collected',
                   data:profArr});
});    

一个简单的想法是在开始这样的for循环之前引入一个倒数计数器:

var countdown = doc.performers.length;

减少findOne-Calls的回调函数中的倒计时。 检查您是否已达到0并在外部调用函数以发送结果。

但是您的代码仍然看起来效率不高。 有很多对数据库的调用。 也许您可以重新考虑数据模型,以最大程度地减少对数据库的调用。

问题是您需要在猫鼬查询内返回响应。 您不能使用外部查询内部分配的任何值。 例如 :

var sampleArr = [];
Users.find({}, function(err, users) {
  users.forEach(function(user) {
    Students.find({'userid' : user.id}, function(err, student) {
      sampleArr.push({
        'student' : student
      });
    })
    console.log(sampleArr);
    // It will only return empty array[];
  })
})

因此,您的任务应如下所示:

apiRoutes.get('/performers/:id', function(req,res,next){

var profArr = [];
// Get a task by ID
Task.findById(req.params.id, function (err, task) {
  // Get all profiles
  Profile.find({}, function (err, profiles) {
    task.performers.forEach(function(taskPerformer) {
      profiles.forEach(function(profile) {
        // Check the performer ID is the same with userID or not
        if (profile._id == taskPerformer.userId) {
          profArr.push({
            price: taskPerformer.price,
            name: profile.name,
            surname: profile.surname
          });
        }
      })
    });
    return res.json({
      success:true,
      message:'Performers data collected',
      data:profArr
    });
  });
})

您的“ for”循环将在findOne完成之前完成。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM