Referencing Another Schema in Mongoose

Referencing another schema in Mongoose

It sounds like the populate method is what your looking for. First make small change to your post schema:

var postSchema = new Schema({
name: String,
postedBy: {type: mongoose.Schema.Types.ObjectId, ref: 'User'},
dateCreated: Date,
comments: [{body:"string", by: mongoose.Schema.Types.ObjectId}],
});

Then make your model:

var Post = mongoose.model('Post', postSchema);

Then, when you make your query, you can populate references like this:

Post.findOne({_id: 123})
.populate('postedBy')
.exec(function(err, post) {
// do stuff with post
});

How to reference another schema in my Mongoose schema?

You can do so by using Population

Population is the process of automatically replacing the specified
paths in the document with document(s) from other collection(s). We
may populate a single document, multiple documents, plain object,
multiple plain objects, or all objects returned from a query.

Suppose your Event Schema is defined as follows:

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

var eventSchema = Schema({
title : String,
location : String,
startDate : Date,
endDate : Date
});

var personSchema = Schema({
firstname: String,
lastname: String,
email: String,
gender: {type: String, enum: ["Male", "Female"]}
dob: Date,
city: String,
interests: [interestsSchema],
eventsAttended: [{ type: Schema.Types.ObjectId, ref: 'Event' }]
});

var Event = mongoose.model('Event', eventSchema);
var Person = mongoose.model('Person', personSchema);

To show how populate is used, first create a person object,

aaron = new Person({firstname: 'Aaron'})
and an event object,

event1 = new Event({title: 'Hackathon', location: 'foo'}):

aaron.eventsAttended.push(event1);
aaron.save(callback);

Then, when you make your query, you can populate references like this:

Person
.findOne({ firstname: 'Aaron' })
.populate('eventsAttended') // only works if we pushed refs to person.eventsAttended
.exec(function(err, person) {
if (err) return handleError(err);
console.log(person);
});

How can i reference a field in another mongoose model so i can retrieve multiple documents from different collections

You will need to reference mongoose model in your schema, instead of schema.

Like:

Subcategory schema

const SubcategorySchema = mongoose.Schema({
category_id: {
type: String, required: true
},
name: {
type: String, required: true
},
status: {
type: Number, default: 0
},
icon: {
type: String, required: false
},
created : {
type : Date,
default: Date.now()
}
});

const SubCategoryModel = mongoose.model('SubCategory', SubcategorySchema);

CategorySchema

const subcategories = require('./Subcategory')

const CategorySchema = mongoose.Schema({
name: {
type: String, required: true
},
icon: {
type: String, required: false
},
status: {
type: Number, default: 0
},
created : {
type : Date,
default: Date.now()
},
subcategories: {
type: mongoose.Schema.Types.ObjectId,
ref: "SubCategory" // this name should be same as the model name specified while declaring model
}
});

Types for referencing another schema in mongoose

Yes, it is possible to use types other than ObjectId for refs, but Mongoose recommends using ObjectIds unless you have a good reason to do otherwise.

From the documentation for Populate:

Note: ObjectId, Number, String, and Buffer are valid for use as refs. However, you should use ObjectId unless you are an advanced user and have a good reason for doing so.

Mongoose: Reference schema in properties or add as an array? which is better

You should have a reference to the user in the PostSchema.

This is the better approach because a user can have multiple posts and if you save the posts in the UserSchema as an array, that array can grow infinitely. This can cause problems because there's a limit on the max size of a mongodb document. Single mongodb document cannot be greater than 16Mb.

Saving Posts in the User schema is better from the performance perspective but considering the limit on the size of mongodb document and the fact that a user can have many posts, a child document (Post) referencing its parent document (User) is the better approach here.

How do I reference another field in mongoDB Schema instead of ObjectID?

You can use mongoose's populate to to this:

Book.
findOne({ ... }).
populate('author').
exec(function (err, book) {
if (err) return handleError(err);
// book.author will now be populated
});

Then, in react you can access the name property on the author object:

function Book(book){
const {title}, {pages}, {descritpion}, {author} = book;
return (
<h1> {title} <h1>
<p>{pages} , {description}<p>
<p>{author.name}<p>
);
}


Related Topics



Leave a reply



Submit