Mongoose: how to use aggregate and find together

后端 未结 2 678
情深已故
情深已故 2021-01-30 13:37

How can I use aggregate and find together in Mongoose?
i.e I have the following schema:

const schema = new Mongoose.Schema({
  created: { type:          


        
相关标签:
2条回答
  • 2021-01-30 14:03

    You can use as the following:

    db.locations.aggregate([
      {$match:{"your find query"}},
      {$project:{"your desired fields"}}
    ])
    

    In the match you can do stuff like:

    {{$match:{name:"whatever"}}
    

    In the project, you can select the fields you want using numbers 0 or 1 like:

    {$project:{_id:1,created:0,name:1}}
    

    Which 0 means, do not put and 1 means put.

    0 讨论(0)
  • 2021-01-30 14:26

    For MongoDB 3.6 and greater, use the $expr operator which allows the use of aggregation expressions within the query language:

    var followers_count = 30;
    db.locations.find({
       "$expr": { 
           "$and": [
               { "$eq": ["$name", "development"] },
               { "$gte": [{ "$size": "$followers" }, followers_count ]}
           ]
        }
    });
    

    For non-compatible versions, you can use both the $match and $redact pipelines to query your collection. For example, if you want to query the locations collection where the name is 'development' and followers_count is greater than 30, run the following aggregate operation:

    const followers_count = 30;
    Locations.aggregate([
        { "$match": { "name": "development" } },
        {
            "$redact": {
                "$cond": [
                    { "$gte": [ { "$size": "$followers" }, followers_count ] },
                    "$$KEEP",
                    "$$PRUNE"
                ]
            }
        }
    ]).exec((err, locations) => {
        if (err) throw err;
        console.log(locations);
    })
    

    or within a single pipeline as

    Locations.aggregate([
        {
            "$redact": {
                "$cond": [
                    { 
                        "$and": [
                            { "$eq": ["$name", "development"] },
                            { "$gte": [ { "$size": "$followers" }, followers_count ] }
                         ]
                    },
                    "$$KEEP",
                    "$$PRUNE"
                ]
            }
        }
    ]).exec((err, locations) => {
        if (err) throw err;
        console.log(locations);
    })
    

    The above will return the locations with just the _id references from the users. To return the users documents as means to "populate" the followers array, you can then append the $lookup pipeline.


    If the underlying Mongo server version is 3.4 and newer, you can run the pipeline as

    let followers_count = 30;
    Locations.aggregate([
        { "$match": { "name": "development" } },
        {
            "$redact": {
                "$cond": [
                    { "$gte": [ { "$size": "$followers" }, followers_count ] },
                    "$$KEEP",
                    "$$PRUNE"
                ]
            }
        },
        {
            "$lookup": {
                "from": "users",
                "localField": "followers",
                "foreignField": "_id",
                "as": "followers"
            }
        }
    ]).exec((err, locations) => {
        if (err) throw err;
        console.log(locations);
    })
    

    else you would need to $unwind the followers array before applying $lookup and then regroup with $group pipeline after that:

    let followers_count = 30;
    Locations.aggregate([
        { "$match": { "name": "development" } },
        {
            "$redact": {
                "$cond": [
                    { "$gte": [ { "$size": "$followers" }, followers_count ] },
                    "$$KEEP",
                    "$$PRUNE"
                ]
            }
        },
        { "$unwind": "$followers" },
        {
            "$lookup": {
                "from": "users",
                "localField": "followers",
                "foreignField": "_id",
                "as": "follower"
            }
        },
        { "$unwind": "$follower" },
        {
            "$group": {
                "_id": "$_id",
                "created": { "$first": "$created" },
                "name": { "$first": "$name" },
                "followers": { "$push": "$follower" }
            }
        }
    ]).exec((err, locations) => {
        if (err) throw err;
        console.log(locations);
    })
    
    0 讨论(0)
提交回复
热议问题