21

I'm quite new to mongodb and there is one thing I can't solve right now:
Let's pretend, you have the following document (simplified):

{
   'someKey': 'someValue',
   'array'  : [
       {'name' :  'test1',
        'value':  'value1'
       },
       {'name' :  'test2',
        'value':  'value2'
       }
    ]
}

Which query would return the json-object, in which the value equals 'value2'?

That means, i need this json-object:

{
    'name' :  'test2',
    'value':  'value2'
}

Of course I already tried a lot of possible queries, but none of them returned the right, e.g.

db.test.find({'array.value':'value2'})
db.test.find({'array.value':'value2'}, {'array.value':1})
db.test.find({'array.value':'value2'}, {'array.value':'value2'})  

Can someone help and show me, what I'm doing wrong?
Thanks!

4 Answers 4

31

Using Positional operator

db.test.find(
    { "array.value": "value2" },
    { "array.$": 1, _id : 0 }
)

Output

{ "array" : [ { "name" : "test2", "value" : "value2" } ] }

Using aggregation

db.test.aggregate([
    { $unwind : "$array"},
    { $match : {"array.value" : "value2"}},
    { $project : { _id : 0, array : 1}}
])

output

{ "array" : { "name" : "test2", "value" : "value2" } }

Using Java Driver

    MongoClient mongoClient = new MongoClient(new ServerAddress("localhost", 27017));
    DB db = mongoClient.getDB("mydb");
    DBCollection collection = db.getCollection("test");

    DBObject unwind = new BasicDBObject("$unwind", "$array");
    DBObject match = new BasicDBObject("$match", new BasicDBObject(
            "array.value", "value2"));
    DBObject project = new BasicDBObject("$project", new BasicDBObject(
            "_id", 0).append("array", 1));

    List<DBObject> pipeline = Arrays.asList(unwind, match, project);
    AggregationOutput output = collection.aggregate(pipeline);

    Iterable<DBObject> results = output.results();

    for (DBObject result : results) {
        System.out.println(result.get("array"));
    }

output

{ "name" : "test2" , "value" : "value2"}
Sign up to request clarification or add additional context in comments.

1 Comment

how do I retrieve some of the parent fields along with the matching nested fields? I am looking for something like this in response: {'someKey': 'someValue','array' : [{ "name": "test2" , "value": "value2"}]}
2

You can pass multiple find objects in element match for getting the exact answer.

db.test.find({'array':{$elemMatch:{value:"value2"}})

output: {'name' :  'test1','value':  'value1'}

Comments

1

Try the $in operator like this:

db.test.find({"array.value" : { $in : ["value2"]}})

1 Comment

Thanks for your help, but unfortunately it doesn't work either. If I run this in the terminal, it returns the whole document
0

Use $elemMatch and dot(.) to get your required output

db.getCollection('mobiledashboards').find({"_id": ObjectId("58c7da2adaa8d031ea699fff") },{ viewData: { $elemMatch : { "widgetData.widget.title" : "England" }}})

Comments

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.