Sie müssen den Gruppierungsschlüssel bedingt bestimmen, basierend darauf, wo das aktuelle Datum in den Bereich fällt. Dies wird im Wesentlichen über $cond
erreicht
mit verschachtelten Bedingungen und der logischen Variante von $lt
:
// work out dates somehow
var today = new Date(),
oneDay = ( 1000 * 60 * 60 * 24 ),
thirtyDays = new Date( today.valueOf() - ( 30 * oneDay ) ),
fifteenDays = new Date( today.valueOf() - ( 15 * oneDay ) ),
sevenDays = new Date( today.valueOf() - ( 7 * oneDay ) );
db.collection.aggregate([
{ "$match": {
"date": { "$gte": thirtyDays }
}},
{ "$group": {
"_id": {
"$cond": [
{ "$lt": [ "$date", fifteenDays ] },
"16-30",
{ "$cond": [
{ "$lt": [ "$date", sevenDays ] },
"08-15",
"01-07"
]}
]
},
"count": { "$sum": 1 },
"totalValue": { "$sum": "$value" }
}}
])
Als $cond
ein ternärer Operator ist, wird die erste Bedingung ausgewertet, um zu sehen, ob die Bedingung wahr ist, und wenn sie wahr ist, wird das zweite Argument zurückgegeben, andernfalls wird das dritte zurückgegeben, wenn sie falsch ist. Also durch Verschachteln eines weiteren $cond
Im falschen Fall erhalten Sie den logischen Test, wo das Datum liegt, entweder "weniger als das 15-Tage-Datum", was bedeutet, dass es im ältesten Bereich liegt, oder "weniger als 7 Tage", was im mittleren Bereich bedeutet, oder natürlich ist es in das neueste Sortiment.
Ich stelle hier nur den Zahlen kleiner als 10 eine 0
voran Sie haben also etwas zum Sortieren, wenn Sie möchten, seit der Ausgabe von "keys" in $group
ist an sich nicht bestellt.
Aber so machen Sie das in einer einzigen Abfrage. Sie berechnen einfach, was der Gruppierungsschlüssel sein sollte, basierend darauf, wo das Datum liegt, und akkumulieren für jeden Schlüssel.