Използване на $where
оператор.
db.collection.find(function() {
return this.docs.length === this.docs.filter(function(doc) {
return typeof(doc.foo) !== "undefined" && doc.foo !== null ;}).length
})
Друг начин да направите това е да стартирате две заявки:Едната за извличане на _id
на всички онези документи, които не отговарят на вашите критерии, като използвате distinct()
метод:
var unwantedIds = db.collection.distinct( "_id", { "docs": { "$elemMatch": { "foo": { "$exists": false } } } } );
След това използвайте $nin
оператор, за да върне всички документи, които отговарят на вашите критерии.
db.collection.find({ "_id": { "$nin": unwantedIds } } )
Можете също да използвате .aggregate()
метод, но това работи само ако сте на версия 3.2 или по-нова, защото трябва да използвате $filter
Първият етап от процеса е $match
етап, в който филтрирате тези документи, в които полето "foo" липсва. Това намалява общия брой документи, които ще бъдат обработени надолу по тръбата. Следващият и последен етап е $redact
сцена. На този етап трябва да използвате $size
оператор за връщане на размера на полето „документи“ и размера на масива от поддокументи, в които присъства „foo“, и връщане на всички онези документи, където двете стойности са равни.
db.collection.aggregate([
{ "$match": { "docs.foo": { "$exists": true } } },
{ "$redact": {
"$cond": [
{ "$eq": [
{ "$size": "$docs" },
{ "$size": {
"$filter": {
"input": "$docs",
"as": "doc",
"cond": {
"$ne": [
{ "$ifNull": [ "$$doc.foo", null ] },
null
]
}
}
}}
]},
"$$KEEP",
"$$PRUNE"
]
}}
])