Reputation: 428
I have this aggregation pipeline:
{
$project: {
type: '$_id.type',
datapoints: [
{$multiply: ['$_id.timestamp', 1000]},
'$count',
],
},
},
{
$group: {
_id: {
type: '$type',
},
datapoints: {$push: '$datapoints'},
},
},
... which brought me to a following question:
How could I possibly append/push/add/etc an array to datapoints
in $group
(what could let me avoid $project
stage))?
If I try putting the same expression for datapoints
in the $project
under $push
in the $group
it gives me an error
Upvotes: 2
Views: 3807
Reputation: 151112
It's a fair point because you cannot just simply notate with "bracket" []
notation as available from MongoDB 3.2 into a $push
.
It's a bit of a hack, but you can basically wrap the expression with $map
instead of using the []
notation:
{ "$group": {
"_id": "$_id.type",
"datapoints": {
"$push": {
"$map": {
"input": [1],
"in": [
{ "$multiply": ["$_id.timestamp", 1000] },
"$count"
]
}
}
}
}}
Or even $concatArrays
if your MongoDB supports it:
{ "$group": {
"_id": "$_id.type",
"datapoints": {
"$push": {
"$concatArrrays": [
[
{ "$multiply": ["$_id.timestamp", 1000] },
"$count"
]
]
}
}
}}
Or even $setUnion
, which is actually probably the shortest to type, but it may not retain the order of elements if that is important to you:
{ "$group": {
"_id": "$_id.type",
"datapoints": {
"$push": {
"$setUnion": [
[
{ "$multiply": ["$_id.timestamp", 1000] },
"$count"
]
]
}
}
}}
Trying to simply do :
"datapoint": { "$push": [{ "$mulitply": [ ...
Will of course result in an error
"errmsg" : "The $push accumulator is a unary operator",
And this sort of expression would be syntactically incorrect:
"datapoint": { "$push": { ["a"] }
So you need an "expression" of some sort which is "unary" and not "list based" and returns a BSON Array in result. The above operators cover those cases.
Upvotes: 4