0

referring to Mongoose url populate example given at https://mongoosejs.com/docs/populate.html#checking-populated , there seems to be a two way relationship between both Schema. What if I only have 1 way relationship for example ( using same schema example, But Person schema does not Story ref )

const mongoose = require('mongoose');
const Schema = mongoose.Schema;

const personSchema = Schema({
  name: String,
  age: Number
});

const storySchema = Schema({
  author: { type: Schema.Types.ObjectId, ref: 'Person' },
  title: String
});

const Story = mongoose.model('Story', storySchema);
const Person = mongoose.model('Person', personSchema);

How can I return a GET Story output that looks like the following :

{
  author :{
    name: "Bla bla bla",
    age: 30
  }
  title : "ABC Story"
}

I am always getting this at the moment :

{
  author :34235245453
  title : "ABC Story"
}
BC2
  • 1,129
  • 1
  • 11
  • 22

2 Answers2

1

I think you are confusing populated() function and populate() function.

To be able to retrieve the author info of a story, we need to use populate like this:

router.get("/stories/:id", async (req, res) => {
  const result = await Story.findById(req.params.id).populate("author");
  res.send(result);
});

Let's say we have this person:

{
    "_id": "5e3c63ba3a178830dc497a00",
    "name": "Name1",
    "age": 33,
    "__v": 0
}

And this story by user:

{
    "_id": "5e3c63e93a178830dc497a02",
    "author": "5e3c63ba3a178830dc497a00",
    "title": "Story1",
    "__v": 0
}

The result will be like this when we send a get request to our route ( http://.../stories/5e3c63f33a178830dc497a02)

{
    "_id": "5e3c63e93a178830dc497a02",
    "author": {
        "_id": "5e3c63ba3a178830dc497a00",
        "name": "Name1",
        "age": 33,
        "__v": 0
    },
    "title": "Story1",
    "__v": 0
}

To get all stories with author info, we can use find() method like this:

router.get("/stories", async (req, res) => {
  const result = await Story.find().populate("author");
  res.send(result);
});
SuleymanSah
  • 17,153
  • 5
  • 33
  • 54
  • Hi @SuleymanSah, if i want a get all stories , I can use .find().populate(‘author’)? I am doing this now but i’m not getting the author information when i send a get all request. The output i’m getting is the 1 i posted – BC2 Feb 07 '20 at 01:38
  • @BC2 yes you can get all stories and author info with code in your comment. Can you show me the full code you used? – SuleymanSah Feb 07 '20 at 04:54
  • i'll try to edit the question to include my example. – BC2 Feb 07 '20 at 15:00
  • I've managed to get my desired output by using Richard Job's example. Thanks for helping me :D – BC2 Feb 07 '20 at 15:03
  • @BC2 my answer should work, his answer is similar to my answer. – SuleymanSah Feb 07 '20 at 15:49
1

I am not sure whether this is a good practise, but you can achieve this as follows

const mongoose = require('mongoose');
const Schema = mongoose.Schema;

const personSchema = Schema({
  name: String,
  age: Number
});

const storySchema = Schema({
  author: Schema.Types.ObjectId, //modified by just defining the type
  title: String
});

const Story = mongoose.model('Story', storySchema);
const Person = mongoose.model('Person', personSchema);

when populating,

SOMETHING.find()
.populate({
   'path':'author',
   'model':'Person'
});
Richard Job
  • 104
  • 1
  • 5
  • THanks Richard. It works. Although I did not include the ' for model. `await Story.find().populate({ 'path':'author', 'model':Person });` i got "Schema hasn't been registered for model" if i use the ' for the value. All is good now . – BC2 Feb 07 '20 at 15:05