Automattic / mongoose

MongoDB object modeling designed to work in an asynchronous environment.
https://mongoosejs.com
MIT License
26.94k stars 3.84k forks source link

lookup operation #13986

Closed chandankumar14 closed 12 months ago

chandankumar14 commented 1 year ago

Prerequisites

Mongoose version

latest

Node.js version

16.x

MongoDB version

latest

Operating system

None

Operating system version (i.e. 20.04, 11.3, 10)

No response

Issue

@vkarpov15 { $lookup: { from: "like_commnents", let: { Id:userId // this is custom value}, pipeline: [{ $match: { $expr: { $eq: ["$userId", "$$Id"] } } }], as: "likes", } }

can we perform lookup operation like this ?

vkarpov15 commented 1 year ago

Sure, I don't see any reason why not. But I don't work with $lookup much, so I could be mistaken. Have you tried this and run into some issue?

Rushikeshkuthe commented 1 year ago

project schema:

import mongoose from "mongoose";

const ProjectSchema = new mongoose.Schema({
  name: {
    type: String,
    required: true,
  },
  code : {
    type: String,
    required: true,
  },
  startDate:{
    type: Date,
    required: true
  },
  clientName:{
    type:String,
    required: true,
  },
  user_id:{
    type: mongoose.Schema.Types.ObjectId,
    ref: 'User', // assuming 'User' is the model name for your user schema
    required: true,
  }
});

export default mongoose.model("Project", ProjectSchema);

User Schema:

import mongoose from "mongoose";

const UserSchema = new mongoose.Schema({
  name: {
    type: String,
    required: true,
  },
  email: {
    type: String,
    required: true,
  },
  password: {
    type: String,
    required: true,
  },
  cpassword: {
    type: String,
    required: true,
  },
  token: {
    type: [String],
  },
});

export default mongoose.model("User", UserSchema);

Project Model::

router.get('/allProjects',async(req,res)=>{
  try {
    const result = await Project.aggregate([
      {
        $lookup: {
          from: 'users', 
          localField: 'user_id',
          foreignField: '_id', 
          as: 'user', 
        },
      },
    ]);

    // console.log(result);
     res.status(200).send({success:true,msg:'Project Data',data:result})
  } catch (error) {
    console.error(error);
  }

})

http request:http://localhost:8000/api/projects/allProjects error:{ "error": "Cast to ObjectId failed for value \"allProjects\" (type string) at path \"_id\" for model \"Project\"" }

Rushikeshkuthe commented 1 year ago

please help me with this error i am facing in mern stack as i am new to this technology.

vkarpov15 commented 1 year ago

Do you have a router.get('/:id') endpoint? Remember that router.get('/:id') matches any string, including 'allProjects', so try switching the order you define your router.get('/:id') and router.get('/allProjects') endpoints.

github-actions[bot] commented 12 months ago

This issue is stale because it has been open 14 days with no activity. Remove stale label or comment or this will be closed in 5 days

akash-gajjar commented 12 months ago

@chandankumar14 you need to convert $$id to string or cast userId to ObjectId, here is one example

{
  $lookup: {
    from: 'like_commnents',
    let: {
      id: userId,
    },
    pipeline: [
      {
        $match: {
          $expr: {
            $eq: [{ $toString: '$userId' }, '$$id'],
          },
        },
      },
    ],
    as: 'likes',
  },
};