2015-10-27 2 views
2

Чтобы узнать стек MEAN (используя Mongoose), я создаю приложение типа StackOverflow. У меня есть вопросы, которые хранятся в Mongo (v3.0.7), и у них есть поддокументы ответа.Mongoose возвращает NULL на findOneAndUpdate()

Я пытаюсь увеличить голос голоса, но когда вопрос возвращается, он равен нулю. Я почти уверен, что что-то не так с запросом, особенно там, где я пытаюсь получить ответ с идентификатором, который мне нужно изменить.

Вопрос Схема:

var questionsSchema = new mongoose.Schema({ 
    answers: [ answerSchema ], 
    }); 

Ответ схемы:

var answerSchema = new mongoose.Schema({ 
    votes: { type: Number, default: 0 }, 
    }); 

Запрашивание _id возвращает нуль:

Question.findOneAndUpdate(
    {_id: req.params.questionId, 'answers._id': req.params.answerId }, 
    { $inc: { 'answers.$.votes': 1 } }, 
    { new: true }, 
    function(err, question){ 
    if (err) { return next(err); } 
    //question is returned as NULL 
    res.json(question); 
    }); 

Запрашивание 0 голосов работы:

Question.findOneAndUpdate(
    {_id: req.params.questionId, 'answers.votes': 0 }, 
    { $inc: { 'answers.$.votes': 1 } }, 
    { new: true }, 
    function(err, question){ 
    if (err) { return next(err); } 
    //question is returned as NULL 
    res.json(question); 
    }); 

UPDATE: запросов через Монго результат возвращается:

db.questions.find({_id: ObjectId('562e635b9f4d61ec1e0ed953'), 'answers._id': ObjectId('562e63719f4d61ec1e0ed954') }) 

НО, через Mongoose, NULL возвращается:

Question.find(
{_id: Schema.ObjectId('562e635b9f4d61ec1e0ed953'), 'answers._id': Schema.ObjectId('562e63719f4d61ec1e0ed954') }, 
+1

Вы пробовали '' answers._id ': ObjectId (req.params.answerId) 'или'' answers._id ': new ObjectId (req.params.answerId) 'или что-то в этом роде? Кроме того, как насчет в CLI MongoDB, он что-то возвращается? –

+0

Только что обновлено: хорошая идея в CLI, которая возвращает документ, но когда я добавляю ObjectID через Mongoose, null все еще возвращается. – Greg

+1

Да, как я уже говорил, вам, вероятно, понадобится 'new ObjectId()' и объявить его в верхней части вашего файла. Это глупо, я все еще не уверен, почему это даже нужно сделать ... –

ответ

2

Попробуйте использовать типы мангуста ObjectID

http://mongoosejs.com/docs/api.html#types-objectid-js:

var ObjectId = mongoose.Types.ObjectId; 
Question.find({ 
    _id: '562e635b9f4d61ec1e0ed953', 
    'answers._id': new ObjectId('562e63719f4d61ec1e0ed954') 
}) 

Окончательный ответ на первоначальный вопрос обновления:

Question.findOneAndUpdate(
    {_id: req.params.questionId, 
    'answers._id': new ObjectId(req.params.answerId) }, 
    { $inc: { 'answers.$.votes': 1 } }, 
    { new: true }, 
    function(err, question){ 
    if (err) { return next(err); } 
    res.json(question); 
    }); 
+0

Это был самый близкий ответ, но он нуждался в модификации. Вы не можете обновлять ObjectId до тех пор, пока вы его не используете. – Greg

+0

Да, это правда, но зачем использовать предлагать использовать новый ObjectId только в одном месте в вашем редактировании (в разделе «answers._id»)? Question.find ({ _id: '562e635b9f4d61ec1e0ed953', 'answers._id': новый ObjectId ('562e63719f4d61ec1e0ed954') }).И я не вижу смысла использовать 2 запроса здесь, поэтому замена find() на findOne ({_ id: "562e635b9f4d61ec1e0ed953"}) должна быть лучшим вариантом здесь IMHO –

+0

Вы можете использовать его в боте, но из моего тестирования его не требуется. Не уверен, как это работает под обложками, но они, вероятно, знают, что «_id» - это ObjectId и выполняет бросок, но, возможно, они не знают, что «answers._id» - это ObjectId .... не знаю, но это образ кода возвращает именно то, что я искал, поэтому спасибо! – Greg

0

Вам не нужно ObjectId вообще:

Question.findOne({_id: "562e635b9f4d61ec1e0ed953"}, callback) 

Mongoose обрабатывает строку для вас.

Кроме того, используя find() и запрос _id приведет к массиву длиной 0 или 1. Использование findOne() вернет объект документа.

Смежные вопросы