I have two mongodb collections, let's call them parents
and children
. This parents/children design has a one-to-many relationship, and when I query the parent I want the children as well. It makes sense to have this model design:
var ParentSchema = new Schema({
name: String,
children: [{type: Schema.Types.ObjectID, ref: 'Child'}]
});
var ChildSchema = new Schema({
name: String
});
That way, I can use populate()
to easily get the children within the parent. However, I've been told that it's not good to use arrays like this, because they can get cluttered. So, if I put the object reference in the ChildSchema
, then I can avoid using an array like that.
var ParentSchema = new Schema({
name: String
});
var ChildSchema = new Schema({
name: String,
parent: {type: Schema.Types.ObjectID, ref: 'Parent'}
});
But if I want to get the children withing the parent again, populate()
won't work. What's the best pattern to use, and if I'm using refs in the children, is there a method similar to populate()
that does this? I don't like having to make two queries to get one result.
My understanding is that the issue with storing an array of references to Children within Parents would be the case where the array of Children is unbounded. If this is not the case, I believe that storing an array of references to Children within Parents is the recommended pattern. In the case that the number of children is very large or unbounded, the docs suggest using Virtuals.
I believe a simple example would look something like...
const ChildSchema = new Schema({
name: String,
parent: String,
});
const ParentSchema = new Schema({
name: String,
});
ParentSchema.virtual('children', {
ref: 'Child', // the model to use
localField: 'name', // find children where 'localField'
foreignField: 'parent' // is equal to foreignField
});
const Parent = mongoose.model('Parent', parentSchema);
const Child = mongoose.model('Child', childSchema);
/*
Let's say we have two parents: Jack and Mindy
And four children: Jake with Jack, and Mike, Molly, and Mildred with Mindy
*/
Parent.find({}).populate('children').exec(function(error, parents) {
/// parents.children is now an array of instances of Child.
});
For more info on population, check out the Mongoose.js docs here mongoosejs.com.
All credit to mongoosejs.com as my example is just an adaptation of theirs. Also, please note that I haven't actually tested this code as I am answering this question on my phone.
Hope this helps.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With