Tang Chanrith
Tang Chanrith

Reputation: 1449

MongoDB: How to query field array by _id

how to get the specific message by _id. I have a database schema as shown below:

{
    "_id": ObjectID("5846eedaf0b51ed02ed846e2"),
    "name": "conversation name"
    "messages": [
        {
            "_id": ObjectID("584820a96866b6283361a4b9"),
            "content": "hello",
            "status": 0,
            "type": 0
        },
        {
            "_id": ObjectID("584820d56866b6283361a4ba"),
            "content": "voices/1481122005696.mp3",
            "status": 0,
            "type": 3
        }
    ]
}

Upvotes: 0

Views: 611

Answers (2)

ztrange
ztrange

Reputation: 305

Since you tagged mongoose, I put it like this, but the query syntax is valid because is part of mongoDB query syntax:

Conversation.findOne({
  "messages._id": "584820a96866b6283361a4b9"
}, function(err, document){
    if (err) {
        console.log(err) 
        return
    }
    var message = document.messages.id("584820a96866b6283361a4b9")
})

The finOne() method will return the full parent document with all the messages (subdocuments) and other properties. You then need to filter out the subdocument. Mongoose provides a way to do this easily with: document.messages.id("584820a96866b6283361a4b9") where document would be the data object passed to the find callback

See: Match a Field Without Specifying Array Index on https://docs.mongodb.com/v3.2/tutorial/query-documents/#query-on-arrays

Upvotes: 1

dyouberg
dyouberg

Reputation: 2332

db.collection.find({}, {
    'messages': {
        $elemMatch: {
            '_id': ObjectId("584820a96866b6283361a4b9")
        }
    }
})

This will match on all documents in your collection, and return the matching array subfield in the projection. See the link posted in Yogesh's comment.

Upvotes: 1

Related Questions