Mongoose: как запросить свойство объекта ссылки?

Я пытаюсь получить список документов из моей базы данных на основе свойства поддокумента. Моделями и схемами, которые я использую, являются:

var elementSchema = new mongoose.Schema({
    name: String,
    description: String,

    _story: { type: mongoose.Schema.Types.ObjectId, ref: 'Story' },

    date_created: Date,
    date_modified: Date,
};
var storySchema = new mongoose.Schema({
    title: {type: String, default: '', trim: true},
    isPrivate: {type: Boolean, default: false},
});

mongoose.model("Story", storySchema);
mongoose.model("Element", elementSchema);

Я пытаюсь получить все Элементы, принадлежащие к Истории, которая не является частной, и согласно некоторым сообщениям, которые я видел здесь (1, 2, 3) было бы использовать _story.isPrivate с find. Я сейчас делаю это:

Element.find({'_story.isPrivate': false})
         .populate('_story')
         .exec(function(err, elements){
             if(err){
                 return next(err);
             }
             else if(elements.length > 0){
                 return res.send(elements);
             }
             else{
                 return res.send(404, {message: "No elements found"});
             }
});

Но результат всегда является пустым (возвращает 404). При отсутствии условия find возвращает все элементы и правильно заполняет _story. Я также активировал вывод отладки, чтобы увидеть выполняемые запросы, и я получаю следующее:

Mongoose: elements.find({ '_story.isPrivate': false }) { fields: undefined, safe: undefined }

Пытаясь выполнить это в MongoDB, я не получаю никаких результатов. Что здесь может быть неправильным?

Спасибо

Ответ 1

Слушайте @JohnnyHK. Он говорит правду. Запросы Mongodb используют данные только в одной и только одной коллекции за раз. Поскольку документы в коллекции "элементы" никогда не имеют ключевого пути _story.isPrivate, Element.find({'_story.isPrivate': false}) никогда не будет соответствовать какому-либо документу. В mongodb нет объединений. В самом деле. Однако, учитывая ограничение "нет соединений", все еще возможно создать приложение и выполнить прецеденты, но вам нужны альтернативные схемы и схемы запросов. Иногда люди денормализуют свои данные и дублируют вещи. Иногда вы запускаете несколько связанных запросов и т.д. И т.д.

Ответ 2

Вы можете повторно заказать свою модель и

var storySchema = new mongoose.Schema({
    title: {type: String, default: '', trim: true},
    isPrivate: {type: Boolean, default: false},
    elements: [{type: mongoose.Schema.Types.ObjectId, ref: 'Element'}]
});

Story.distinct('elements', {'isPrivate':false}, function(error, results) { 
  /* handle callback */ 
}

Таким образом, вы можете выдать один вызов и получить aggragate из Elements.