2015-05-12 3 views
1

, распространяющий этот следующий вопрос: MongoDB filter multi sub-documents, который я хочу отфильтровать документ, чтобы показывать только активные поддокументы: активные автомобили и активные фрукты.mongoDB Aggregation retuns empty

Использование сборки агрегация трубопровода по chridam в следующем документе, где все fruits отключены

{ 
    "name":"Andre", 
    "fruits":[ 
     { 
      "active":false, 
      "fruitname":"apple" 
     },{ 
      "active":false, 
      "fruitname":"banana" 
     } 
    ], 
    "cars":[ 
     { 
      "active":false, 
      "carname":"ford" 
     },{ 
      "active":true, 
      "carname":"GM" 
     }, 
    ] 
} 

агрегация трубопровода используется:

var pipeline = [ 
{ 
    "$match": { 
     "name": "Andre", 
     "fruits.active": true, 
     "cars.active": true 
    } 
}, 
{ "$unwind": "$fruits" }, 
{ "$unwind": "$cars" }, 
{ 
    "$match": {    
     "fruits.active": true, 
     "cars.active": true 
    } 
}, 
{ 
    "$group": { 
     "_id": { 
      "_id": "$_id", 
      "name": "$name" 
     }, 
     "cars": { "$addToSet" : "$cars" }, 
     "fruits": { "$addToSet" : "$fruits" } 
    } 
}, 
{ 
    "$project": { 
     "_id": 0, 
     "name": "$_id.name", 
     "cars": 1, 
     "fruits": 1 
    } 
}  
] 

m_object.aggregate(pipeline) 
     .exec(function (err, result) { 
      if (err) { 
       console.log(err); 
       return; 
      } 
      console.log('result'); 
     }); 

вместо того, чтобы

[{ 
    "name":"Andre", 
    "fruits":[], 
    "cars":[ 
     { 
      "active":true, 
      "carname":"GM" 
     }, 
    ] 
}] 

агрегацию возвращается

[] 

ответ

1

Попробуйте следующий агрегацию трубопровод, он не возвращает пустой массив для неактивных элементов, но ближе к результату:

db.collection.aggregate([ 
    { 
     "$match": { 
      "name": "Andre", 
      "$or": [ 
       { "fruits.active": true }, 
       { "cars.active": true } 
      ] 
     } 
    }, 
    { "$unwind": "$fruits" }, 
    { "$unwind": "$cars" }, 
    { 
     "$match": {    
      "$or": [ 
       { "fruits.active": true }, 
       { "cars.active": true } 
      ] 
     } 
    }, 
    { 
     "$project": { 
      "name": 1, 
      "active_cars": "$cars.active", 
      "active_fruits": "$fruits.active", 
      "cars": 1, 
      "fruits": 1 
     } 
    }, 
    { 
     "$project": { 
      "name": 1, 
      "cars": { 
       "$cond": [ 
        { "$eq": ["$active_cars", true] }, 
        "$cars", 
        {} 
       ] 
      }, 
      "fruits": { 
       "$cond": [ 
        { "$eq": ["$active_fruits", true] }, 
        "$fruits", 
        {} 
       ] 
      } 
     } 
    }, 
    { 
     "$group": { 
      "_id": { 
       "_id": "$_id", 
       "name": "$name" 
      }, 
      "cars": { "$addToSet" : "$cars" }, 
      "fruits": { "$addToSet" : "$fruits" } 
     } 
    }, 
    { 
     "$project": { 
      "_id": 0, 
      "name": "$_id.name", 
      "cars": 1, 
      "fruits": 1 
     } 
    }  
]) 

Выходной

/* 1 */ 
{ 
    "result" : [ 
     { 
      "cars" : [ 
       { 
        "active" : true, 
        "carname" : "GM" 
       } 
      ], 
      "fruits" : [{}], 
      "name" : "Andre" 
     } 
    ], 
    "ok" : 1 
} 
0

Давайте посмотрим на самой первой операции, критерии запроса, в трубопроводе:

"$match": { 
    "name": "Andre", 
    "fruits.active": true, 
    "cars.active": true 
} 

На английском языке: «найти меня все документы name = Andre где есть по крайней мере один активный плод и хотя бы один активный автомобиль. "

Так вы явно с просьбой не, чтобы получить какие-либо результаты, где нет активных фруктов и автомобилей, следовательно, результат пуст.