1

In my collection:

{ "code": xx1
  "valueList": [
                  { "id": "yy1", "name": "name1"},
                  { "id": "yy2", "name": "name2"},
                  { "id": "yy3", "name": "name3"}              
               ]
},
{ "code": xx2
  "valueList": [
                  { "id": "yy4", "name": "name4"},
                  { "id": "yy5", "name": "name5"},
                  { "id": "yy6", "name": "name6"}              
               ]
}

I want to return specific ONE matching subdocument (not an array), like below:

{ "id": "yy3", "name": "name3"}  

I try below code:

findOne({ "code": "xx1",
          "valueList.name": "yy3"
       })
.select({ "valueList.$": 1});

It returns an array instead:

 {
   "valueList": [{ "id": "yy3", "name": "name3" }]
 }

How can I solve this? Thank you

0

1 Answer 1

1

You can use below aggregation:

db.col.aggregate([
    { $match: { "valueList.id": "yy3" } },
    { $unwind: "$valueList" },
    { $match: { "valueList.id": "yy3" } },
    { $replaceRoot: { newRoot: "$valueList" } }
])

First $match will filter out all unnecessary documents, then you can use $unwind to get valueList item per document and then $match again to get only the one with yy3 in the last stage you can use $replaceRoot to promote valueList item to the top level.

Sign up to request clarification or add additional context in comments.

2 Comments

It works but is returning an array: [{ "id": "yy3", "name": "name3"} ]. Is it possible it can just return the subdocument itself without the array: { "id": "yy3", "name": "name3"} (note: without the [ ])? It will be perfect then, thank you
@elvin, that needs to be handled in your app logic, aggregate and find will always return an array, even if it's one-element array

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.