2015-02-11 114 views
1

我掙扎從最近2小時更新我的​​嵌套集合。有人可以嘗試引導我正確的方向嗎?更新嵌套的查詢在貓鼬

var ChoiceSchema = new Schema ({ 
    body: {type: String, required: true}, 
    correct: {type: Boolean, required: true}, 
    timesDisplayed: {type: Number, default: 0}, 
    timesSelected: {type: Number, default: 0}, 
    images: {} 
}); 

var QuestionSchema = new Schema({ 
    contentId: {type: String, required: true}, 
    questionBody: {type: String, required: true}, 
    timesAnswered: {type: Number, default: 0}, 
    timesCorrect: {type: Number, default: 0}, 
    timesIncorrect: {type: Number, default: 0}, 
    timesSkipped: {type: Number, default: 0}, 
    explanation: { 
    contentId: {type: String, required: true}, 
    body: {type: String, required: true}, 
    images: {} 
    }, 
    images: {}, 
    choices: [ChoiceSchema] 
}); 

var ExamSchema = new Schema ({ 
    subject: {type: String, required: true}, 
    dateCreated: { type: Date, default: Date.now }, 
    examNumber: Number, 
    section1: { 
    part1: { 
     timeInMinutes: Number, 
     instructions: {type: String, required: true}, 
     questions: [QuestionSchema] 
    }, 
    part2: {} 
    }, 
    section2: {} 
}); 

我正在嘗試更新QuestionsSchema中的timesAnswered屬性。

Exam.findById(req.params.id, function (err, exam) { 
    var ids=JSON.parse(req.body.ids); 
    if(err) { return handleError(res, err); } 
    if(!exam) { return res.send(404); } 
    if(ids.length) { 
     for(var i=0;i<ids.length;++i){ 
     Exam.update({'section1.part1.questions.$._id':ids[i]}, 
      { $set: { 
       'section1.part1.questions.$.timesAnswered': 1 // <== and here 
      }}, function (err, numAffected) { 
       if(err) throw err; 
      } 
     ); 
     } 
    } 
    return res.json(exam); 
    }); 

其中IDS是包含數組的問題ID

[ '54db8ee6529b197018822eb4', 
    '54db8ee6529b197018822ea7', 
    '54db8ee6529b197018822ea0' ] 

我引用這個問題,但我不知道爲什麼它不適合我的工作了。 Mongoose nested document update failing?

+0

'Exam.update'是異步的,所以當你調用'回報res.json(考試)','的對象exam'沒有更新呢。 – 2015-02-11 18:03:57

+0

@RodrigoMedeiros即使我只是用'return true'替換它,那麼它也行不通。所以我不能理解最新的錯誤。 – 2015-02-11 18:07:29

+0

究竟是什麼錯誤?有錯誤嗎? – 2015-02-11 19:19:06

回答

1

你代碼有兩個問題。

首先,@yazarubin指出的那樣,您的更新狀況有一個不必要的$,所以只是將其刪除:

Exam.update({'section1.part1.questions._id':id}, 

其次,你正在運行的更新任務(異步任務),一個標準for內(同步),所以它不會等待更新任務完成。在這種情況下,你可以使用async.each功能:

var async = require('async'); // be sure to install and require the async module 

async.each(ids, function (id, callback) { 
    Exam.update({'section1.part1.questions._id':id}, 
    { $set: { 
     'section1.part1.questions.$.timesAnswered': 1 // <== and here 
    }}, function (err, numAffected) { 
     if(err) throw err; 
     callback(); 
    } 
); 
}, function (error) { 
    if (error) res.send(500); 
    res.send(exam); // send the response just when all tasks has finished 
}); 

,或者你可以使用某種承諾庫來完成這個相同的任務。

+0

它工作完美.. – 2015-02-24 02:12:06

0

你可以嘗試:

Exam.findById(req.params.id, function (err, exam) { 
    var ids=JSON.parse(req.body.ids); 
    if(err) { return handleError(res, err); } 
    if(!exam) { return res.send(404); } 
    if(ids.length) { 
     for(var i=0;i<ids.length;++i){ 
      var question=exam.section1.part1.questions.id(ids[i]); 
      question.timesAnswered=1; 
     } 
     exam.save(function(err) { 
      if(err) throw err; 
     }); 
    } 
    return res.json(exam); 
}); 
1

這個查詢要做到你想要做什麼(你並不需要查找子句中的$):

Exam.update({'section1.part1.questions._id':ids[i]}, { 
    $set: { 
    'section1.part1.questions.$.timesAnswered':1 
    }}, function(err, numAffected){ 

    })