MongoDB: using $all operator to match arrays (with examples)

Updated: February 3, 2024 By: Guest Contributor Post a comment

Overview

MongoDB, the popular NoSQL database, offers a wide range of query operators that allow developers to perform complex searches with ease. One useful operator in the MongoDB query language is $all, which belongs to the family of array operators. This operator enables you to select documents where the value of an array field contains all the specified elements, regardless of their order or presence of additional elements beyond the query. This tutorial aims to delve into the usage of the $all operator through various examples, beginning with basic usages and progressing to more advanced applications.

Basic Usage of $all

To start with a simple example, let’s consider a MongoDB collection named inventory that stores documents representing stock items. A document in this collection might look like this:

{
    "_id": ObjectId("507f191e810c19729de860ea"),
    "item": "journal",
    "tags": ["blank", "lined", "dotted"]
}

Now, if you needed to find items that are both blank and lined, regardless of any additional tags, you could use the $all operator as follows:

db.inventory.find({
    "tags": { "$all": ["blank", "lined"] }
})

The above query returns documents where the tags array contains both “blank” and “lined” tags.

Combining $all with other Array Operators

When you require a combination of conditions, MongoDB allows you to combine the $all operator with other operators, such as $size and $elemMatch. For instance, if you want to find arrays that contain all the given elements and also want to specify the size of the array, you could write a query like the following:

db.inventory.find({
    "tags": { "$all": ["blank", "lined"], "$size": 2 }
})

This will match documents where the tags array contains exactly the elements “blank” and “lined”, and has no other elements since the size is specified as 2.

Working with Nested Documents

The $all operator can also be used in conjunction with nested documents. Let’s say our inventory items have nested details within an info field, something like this:

{
    "_id": ObjectId("507f191e810c19729de860eb"),
    "item": "planner",
    "info": {
        "format": [
            { "type": "day", "pages": 365 },
            { "type": "week", "pages": 52 }
        ]
    }
}

To find items that have both day and week formats, you might write a query that looks like this:

db.inventory.find({
    "info.format.type": { "$all": ["day", "week"] }
})

However, using the $all operator with nested documents can get more complex when you need to match against multiple fields within the nested documents. In these cases, you may need to use the $elemMatch operator in conjunction with $all.

Advanced Examples

Let’s take your queries to the next level. For example, suppose you have documents where each document’s tags field is an array of subdocuments, each with value and score fields:

{
    "_id": ObjectId("507f191e810c19729de860ec"),
    "item": "notebook",
    "tags": [
        { "value": "red", "score": 10 },
        { "value": "blue", "score": 5 }
    ]
}

If you want to find items tagged both red and blue with a score of 8 or more, you could use $all along with $elemMatch like this:

db.inventory.find({
    "tags": {
        "$all": [
            { "$elemMatch": { "value": "red", "score": { "$gte": 8 } } },
            { "$elemMatch": { "value": "blue", "score": { "$gte": 8 } } }
        ]
    }
})

Note that the above query will not return any documents as both conditions are not satisfied according to our example document.

Performance Considerations

When leveraging the $all operator, especially with large datasets, it is important to consider indexing. Use MongoDB’s indexing capabilities to speed up the search for relevant arrays. Creating an index on the array field could greatly increase the efficiency of queries using the $all operator.

Conclusion

The $all operator is a versatile tool when querying against array fields in MongoDB. As we have seen in the examples, it can be adapted for various situations, from simple array element matching to complex queries on nested documents. Remember to employ indexing strategies to optimize the performance of your queries utilizing the $all operator. By mastering this operator, you can write more efficient and robust MongoDB queries that leverage the full power of your data structures.