Ayyanar G
Ayyanar G

Reputation: 1545

MongoDB: Find a document that matches a condition in all its subdocument

I am trying to write a mongo query to fetch the result that satisifes a condition on all its subdocument,

1. { 
    "_id" : 1, 
    "data" : [
        {
            "Id" : "513", 
            "Nom" : "alouale pfouga", 
        }
    ], 
    "campaigns" : [
        {
            "user" : "1", 
            "latest" : NumberInt(0),             
            "postcode" : [
                [

                ]
            ], 
        }, 
        {
            "user" : "2", 
            "latest" : NumberInt(1), 
            "postcode" : [
                {
                    "id" : "772", 
                    "name" : "xxx", 
                }
            ], 

        }
    ], 

}

2. { 
    "_id" : 2, 
    "data" : [
        {
            "Id" : "514", 
            "Nom" : "pfouga remi", 
        }
    ], 
    "campaigns" : [
        {
            "user" : "1", 
            "latest" : NumberInt(0),             
            "postcode" : [
                [

                ]
            ], 
        }, 
    ], 

}

I need to find the record that has "Postcode" array is empty. As far as I understand query like this: db.users.find({"campaigns.postcode":[]}) gives me both records, but i need only record 2 , because record 1 has postcode node in one sub documents, Please anyone help me !!!

Upvotes: 4

Views: 1081

Answers (2)

Disposer
Disposer

Reputation: 6371

This would give you the answer:

db.test.find({ 'campaigns.postcode': { $size: 0 } } )

but in your case 'campaigns.postcode' has an empty array in it and that means the size is not 0, its 1

You should remove your empty array

"postcode" : [
   [
   ]
], 

should be

"postcode" : []

Updated: After spending some time on the question I realized the problem

For converting "postcode" : [[]] to "postcode" : [] you can use this code:

db.test.find({ 'campaigns.postcode': []} ).forEach(function(item){
    for(var i0 = 0; i0 < item.campaigns.length; i0++)
    {        
        if(item.campaigns[i0].postcode[0].length == []) item.campaigns[i0].postcode = [];
    }

    db.test.update({'_id' : item._id}, item);
});

after that you can find your proper result with:

db.test.find({ 'campaigns.postcode': { $size: 0 }, 'campaigns': { $size: 1 } } )

Upvotes: 4

Neo-coder
Neo-coder

Reputation: 7840

In your json structure it contains

"postcode" : [ [ ] ],

So I tried some but not found exact what you want in expected results I found postcode data where all postcode was empty using following aggregation

db.collectionName.aggregate({"$unwind":"$campaigns"},
     {"$unwind":"$campaigns.postcode"},
      {"$match":{"campaigns.postcode":{"$size":0}}})

Upvotes: 1

Related Questions