Poiché il tuo requisito è semplicemente "proiettare" il documento in modo che il campo sia mascherato, sì, il framework di aggregazione è uno strumento per farlo. Ci vuole un po' per capire il processo durante lo svolgimento degli array e la ricostruzione.
Quindi quello che volevi era questo:
db.collection.aggregate([
{ "$unwind": "$questions" },
{ "$unwind": "$questions.answers" },
{ "$group": {
"_id": {
"_id": "$_id",
"name": "$name",
"description": "$description",
"qid": "$questions._id",
"question": "$questions.question"
},
"answers": {
"$push": {
"_id": "$questions.answers._id",
"answer": "$questions.answers.answer"
}
}
}},
{ "$project": {
"questions": {
"_id": "$_id.qid",
"question": "$_id.question",
"answers": "$answers"
}
}},
{ "$sort": { "_id": 1, "questions._id": 1 } },
{ "$group": {
"_id": "$_id._id",
"name": { "$first": "$_id.name" },
"description": { "$first": "$_id.description" },
"questions": { "$push": "$questions" }
}}
])
Ma in realtà, se hai una versione MongoDB 2.6 o successiva, non è necessario $unwind
e $group
i risultati di nuovo insieme per omettere quel campo. Ora puoi semplicemente farlo usando $project
e $map
operatore che funziona con gli array:
db.collection.aggregate([
{ "$project": {
"name": 1,
"description": 1,
"questions": {
"$map": {
"input": "$questions",
"as": "q",
"in": {
"$ifNull": [
{
"_id": "$$q._id",
"question": "$$q.question",
"answers": {
"$map": {
"input": "$$q.answers",
"as": "el",
"in": {
"$ifNull": [
{ "_id": "$$el._id", "answer": "$$el.answer" },
false
]
}
}
}
},
false
]
}
}
}
}}
])
Ci scusiamo per il rientro che scorre un po' fuori dalla pagina, ma è comunque più facile da leggere in confronto.
Il primo $map
elabora l'array di domande sul posto e invia a un $map
che restituisce i documenti dell'array di risposte interne senza il campo "isCorrectAnswer". Utilizza le proprie variabili per rappresentare gli elementi e l'utilizzo di $ifNull
in c'è solo perché la parte "in" di $map
l'operatore si aspetta di valutare una condizione su ciascuno di questi elementi.
Nel complesso un po' più veloce, poiché non è necessario passare attraverso il $unwind
e $group
operazioni solo per rimuovere il campo. Quindi diventa davvero solo la "proiezione" che potresti aspettarti.