如何填充对存储为同一父文档的子文档的子文档的引用

时间:2015-11-14 00:00:02

标签: mongoose mongoose-schema

哇,这个标题很难读懂。好吧,我坚持一些应该非常简单的事情。我的架构看起来像:

var mongoose = require('mongoose'),
  Schema = mongoose.Schema,
  TrackedVariableSchema = mongoose.model('TrackedVariable').schema;

var ChallengeSchema = new Schema({
  title: {
    type: String,
    default: '',
    trim: true,
    required: 'Title cannot be blank'
  },
  trackedVariables: [TrackedVariableSchema],
  entryConditions: [{
    trackedVar: {
      type: Schema.ObjectId,
      ref: 'TrackedVariable'
    },
    comparison: {
      type: String,
      default: '=='
    },
    compValue: String
  }]
});

mongoose.model('Challenge', ChallengeSchema);

并且,TrackedVariableSchema看起来像:

var mongoose = require('mongoose'),
  Schema = mongoose.Schema;

var types = 'Boolean String Number'.split(' ');
var TrackedVariableSchema = new Schema({
  label: String,
  type: {
    type: String,
    enum: types,
    default: 'String'
  },
  defaultValue: String
});

mongoose.model('TrackedVariable', TrackedVariableSchema);

每个Challenge对象都维护一个TrackedVariables的内部列表。 (A' TrackedVariable'只是我们要为该挑战跟踪的数据的数据定义,但这并不是非常重要。)我宁愿将TrackedVariables作为一个子数组来保持他们的父母挑战。我宁愿不把它们放在自己的收藏中。

我的例子有点模糊,因为这些实体名称没有直观意义,但希望你能看到我想要做的事情。

当我将findById()作为单个Challenge对象,并希望查看每个Condition的每个TrackedVariable的标签时,问题就出现了。像这样:

{
  "_id": "A1"
  "title": "Make a Sandwich",
  "trackedVariables": [{
    "_id": "B1",
    "label": "Slices of bread",
    "type": "Number",
    "default": "0"
  }, {
    "_id": "B2",
    "label": "Has peanut butter",
    "type": "Boolean",
    "default": "false"
  }, {
    "_id": "B3",
    "label": "Has jam",
    "type": "Boolean",
    "default": "false"
  }],
  "entryConditions": [{
    "trackedVar": {
      "_id": "B1",
      "label": "Slices of bread",
      "type": "Number",
      "default": "0"
    },
    "comparison": ">=",
    "compValue": "2"
  }, {
    "trackedVar": {
      "_id": "B2",
      "label": "Has peanut butter",
      "type": "Boolean",
      "default": "false"
    },
    "comparison": "==",
    "compValue": "true"
  }, {
    "trackedVar": {
      "_id": "B3",
      "label": "Has jam",
      "type": "Boolean",
      "default": "false"
    },
    "comparison": "==",
    "compValue": "true"
  }]
}

当然,TrackedVariables没有填充,所以我得到类似的东西:

{
  "_id": "5641adcc918df5901b1e1043",
  "title": "Make a Sandwich"
  "trackedVariables": [{
    "_id": "12345",
    "label": "Slices of bread",
    "type": "Number",
    "default": "0"
  }, {
    "_id": "23456",
    "label": "Has peanut butter",
    "type": "Boolean",
    "default": "false"
  }, {
    "_id": "34567",
    "label": "Has jam",
    "type": "Boolean",
    "default": "false"
  }],
  "entryConditions": [{
    "trackedVar": "B1",
    "comparison": ">=",
    "compValue": "2"
  }, {
    "trackedVar": "B2",
    "comparison": "==",
    "compValue": "true"
  }, {
    "trackedVar": "B3",
    "comparison": "==",
    "compValue": "true"
  }]
}

这不可能,因为我需要生成一个看起来像这样的列表:

挑战入境要求:

Entry Conditions for this Challenge
===================================
Slices of bread      >=     2
Has peanut butter    ==     true
Has jam              ==     true

没问题。只需使用populate(),对吧?

这也是我的想法。而且,如果TrackedVariables存储在他们自己的集合中(而不是作为Challenge的内部子块),这可以正常工作。但是,我尝试过的任何内容都不会为每个entryCondition填充TrackedVariable提供Challenge对象。

我几乎尝试过以下几种我能想到的排列:

Challenge.findById(id)
  .populate('entryConditions.trackedVar')
  .exec(function(err, challenge) {
  ...
...

无论我沿着这些行做什么,trackedVar总是评估为id,或者为null(取决于我尝试的)。我怀疑这与以下事实有关:在响应中,trackedVariables集合已经完全填充。而且,要在entryConditions集合中复制这些数据,那么......好吧......复制。

我真的很难过。好像它应该是微不足道的。

0 个答案:

没有答案