Home > Enterprise >  unable to push object returned from mongoose query
unable to push object returned from mongoose query

Time:12-16

I am making a social media backend. I save post added by the used in a Post model and user data in a User model. GITHUB_REPO_LINK_AT_END

NOTE: UserSchema have a Schema.TypesOf.ObjectId Reference To POST Model. User_Model_&_Post_Model_are_provided_in_the_end

To get all posts of a particular user, I make a GET request to the route "/post" with body:

{ "id" : "6399d54c00308a2fe0bdf9fc"} //sending user id to fetct all the ID of the post from USER model, so i can then query the POST model for the posts

This the function I am getting problem with:

const getPost = async(req, res)=>{
    if(req.body.id){
        try {
            const user = await User.findById(req.body.id).select('-_id post');
            //THIS IS THE PART I NEED HELP WITH-------------------------------------------
            const posts = await user.post.map(async(postID) => {
                const result = await Post.findById(postID).select('-_id title body');
                //console.log(result) THIS PRINTS THE CORRECT OBJ FROM DB
                return result; //THIS RETURNS AN EMPTY OBJECT HERE
            });
            //----------------------------------------------------------------------------
            res.status(200).json(posts);
        } catch (error) {
            console.log(error);
            res.status(500).json({message: error.message});
        }
    }
};

when sending a GET request it returns an empty array with empty objects.//PS: no. of empty obj = actual no. of obj in DB

//This is the response 
[{},{},{},{},{},{},{},{},{},{},{}]
{
  //This is the user object
  "_id": "6399d54c00308a2fe0bdf9fc",
  "createdAt": "2022-12-14T13:52:40.483Z",
  "name": "ShivamUttam",
  "username": "Fadedrifleman",
  "post": [
    "6399d57200308a2fe0bdfa00",
    "6399d5c400308a2fe0bdfa06",
    "6399d5ca00308a2fe0bdfa0a",
    "6399d5d600308a2fe0bdfa0e",
    "6399de29e8aa8697299941c5",
    "6399dec6e9b79ac66c59cd7a",
    "6399df0dbea937f8b3365979",
    "6399df31bea937f8b336597d",
    "6399df31bea937f8b3365981",
    "6399df32bea937f8b3365985",
    "6399df33bea937f8b3365989"
  ],
  "__v": 5
}

Model for USER and POST:

User:

const mongoose = require('mongoose');
const userSchema = new mongoose.Schema({
    createdAt: {
        type: Date,
        default: Date.now()
    },
    name: {
        type: String,
        required: [true, 'name must be provided'],
    },
    username : {
        type: String,
        required: [true, 'Username must be provided'],
    },
    post:[{
        type: mongoose.Schema.Types.ObjectId,
         ref: 'Post',
    }],
});
module.exports = mongoose.model('User', userSchema)

Post:

const mongoose = require('mongoose')
const postSchema = new mongoose.Schema({
    createdAt: {
        type: Date,
        default: Date.now()
    },
    title:{
        type: String,
        required: [true, "title cannot be empty"],
        max: [20, "title cannot exceed 20 character"]
    },
    body: {
        type: String,
        max: [145, "body cannot exceed 145 character"],
    },
    tags:{
        type: String,
    },
});
module.exports = mongoose.model('Post', postSchema);

https://github.com/Fadedrifleman/socialMediaAppBackend/tree/master

CodePudding user response:

Since you have used async callback function in the map method, a async function always return a promise, whatever the entity is returned by the function is wrapped inside a promise and that promise is returned.

If you want to use map function with async js code, you can try the following

const posts = await Promise.all(user.post.map(async(id)=>{
    const result = await Post.findById(postID).select('-_id title body');
    return result;
}));

and if you want to straightaway send the posts, you can also use .lean() method on posts, as in

await Post.findById(postID).select('-_id title body').lean()

CodePudding user response:

You had some bugs that probably would interfere, I did a pull request to fix them: https://github.com/Fadedrifleman/socialMediaAppBackend/pull/1

But the main part would be this:

const getPost = async (req, res) => {
    try {
        if (req.body.id) {
            const user = await User.findById(req.body.id);
            await user.populate("post");
            res.status(200).json(user.post);
            return;
        }

        const posts = await Post.find({ access: 'public' }).select('-access');
        res.status(200).json(posts);
    } catch (error) {
        res.status(500).json({ message: error.message });
    }
};
  • Related