简体   繁体   中英

Mongodb find query based on an array field

The collection:

{
         "_id" : ObjectId("57506d74c469888f0d631be6"),
         "name" : "mycollection",
         "details" : [ 
             {
                 "date" : "25/03/2020",
                 "number" : "A",
                 "active" : false
              }
        },
{
        "_id" : ObjectId("57506d74c469888f0d631usi"),
        "name" : "newcollection",
        "details" : [ 

            {
                "date" : "30/03/2020",
                "number" : "C",
                "active" : false
            } 
        },
{
        "_id" : ObjectId("57506d74c4633388f0d631usi"),
        "name" : "mycollection",
        "details" : [ 

            {
                "date" : "31/03/2020",
                "number" : "C",
                "active" : false
            }
        },
    }

The find query to get the values based on the active status inside the details field.

I have tried:

db.collection.find(
    {"name": "mycollection", "details": {"active": False}})

Expected result: I need the collections where the active is false under details field in each collection. For here record id ObjectId("57506d74c469888f0d631be6") and ObjectId("57506d74c4633388f0d631usi") should be displayed.

The docs contain a section on this type of query here: https://docs.mongodb.com/manual/tutorial/query-array-of-documents/

Your query doesn't work because that syntax requires the array to contain that exact object, but documents in your array contain extra fields, so none match.

The query for this case is db.collection.find({"name": "mycollection", "details.active": False}) .

Note: this will return all documents where the array contains objects with active==false, but it won't filter the actual arrays to remove any elements with active=true.

If details array may have some objects with active = true, and some objects = false, and you need to get only the objects that have active = false, then we can use $filter in aggregation pipeline to filter the details array

your query maybe something like that

db.collection.aggregate([
  {
    $match: {
      name: "mycollection",
      "details.active": false
    }
  },
  {
    $project: {
      name: 1,
      details: {
        $filter: {
          input: "$details",
          as: "elem",
          cond: {
            $eq: ["$$elem.active", false]
          }
        }
      }
    }
  }
])

you can test it here

hope it helps

The query for mongodb or robomongo is the same as in your case the find() might work, but I choose aggregate which could filter the values.

Example query:

db.getCollection('collection').aggregate([{$match: {'details.active': {$ne: true},"name":"mycollection"}}]) 

Simple. But kindly verify and revert.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM