-1

I have a document having array structure in MongoDB. How can I sort the array element in ascending order?

The below is the Input:

{
    "id": 1,
    "name": "sanjay",
    "address": "Odisha",
    "shoes": [
        {
            "brand": "puma",
            "size": "10"
        },
        {
            "brand": "bata",
            "size": "11"
        },
        {
            "brand": "rebook",
            "size": "9"
        },
        {
            "brand": "adidas",
            "size": "7"
        },
        {
            "brand": "bata",
            "size": "8"
        }
    ]
}

Can anyone help me to get a query to sort my all array element in ascending order of the key "size"?

The below is the required output.

{
    "id": 1,
    "name": "sanjay",
    "address": "Odisha",
    "shoes": [
        {
            "brand": "adidas",
            "size": "7"
        },
        {
            "brand": "bata",
            "size": "8"
        },
        {
            "brand": "rebook",
            "size": "9"
        },
        {
            "brand": "puma",
            "size": "10"
        },
        {
            "brand": "bata",
            "size": "11"
        }
    ]
}

Could you please help me to find out the exact query?

Regards, Sanjay

TechWisdom
  • 3,960
  • 4
  • 33
  • 40
  • This post answers your questions. You need to use the aggregation feature to unwind the array and then sort it. http://stackoverflow.com/questions/13449874/how-to-sort-array-inside-collection-record-in-mongodb – sunny Jul 18 '15 at 13:46

1 Answers1

1

In your sample data, shoes.size is a string type. Before sorting, you need to change it to Int. You can use following query to do it.

db.collection.find().forEach(function(data) {
    for (var ii = 0; ii < data.shoes.length; ii++) {
    printjson(data._id);
    print(data.shoes[ii].size);
    db.shoe.update({
        "_id": data._id,
        "shoes.size": data.shoes[ii].size
    }, {
        "$set": {
            "shoes.$.size": parseInt(data.shoes[ii].size)
        }
    });
    }
});

After changing it use aggregation to sort shoes array by following query:

db.collection.aggregate({
    $unwind: "$shoes"
}, {
    $sort: {
    "shoes.size": 1
    }
}, {
    $group: {
    _id: "$_id",
    "shoes": {
        "$push": "$shoes"
    },
    "name": {
        $first: "$name"
    }
    }
}).pretty()

Edit

If you want to select for specific brand then add criteria in match condition.

db.collection.aggregate({
    $unwind: "$shoes"
}, {
    $match: {
    "shoes.brand": "bata"
    }
}, {
    $sort: {
    "shoes.size": 1
    }
}, {
    $group: {
    _id: "$_id",
    "shoes": {
        "$push": "$shoes"
    },
    "name": {
        $first: "$name"
    }
    }
}).pretty()
Vishwas
  • 6,967
  • 5
  • 42
  • 69