How to get depended max value from another max value? - mongodb

Assume there are documents with following structure in the collection:
{
_id: ObjectId("63af57637d4f4258c1ba460b"),
metadata: {
billYear: 2022,
billNumber: 1
}
},
{
_id: ObjectId("63af57637d4f4258c1ba460c"),
metadata: {
billYear: 2022,
billNumber: 2
}
},
{
_id: ObjectId("63af57637d4f4258c1ba460d"),
metadata: {
billYear: 2023,
billNumber: 1
}
}
I need to get the max value of billYear and within this year the max value of billNumber. So in this example the max year is 2023 and the max value in this year is 1.
I tried this attempt:
Data.aggregate( [ { $max : { billNumber : "$billYear" } } ] )
Update
Data.aggregate([{ $group: { _id: null, maxBillYear: { $max: "$metadata.billYear" }}} ])
gives me the max year value:
[ { _id: null, maxBillYear: 2023 } ]
So I would think of running a second query with this year to get the max value for the number. But is it possible to do this directly in a single query?

as for your first attempt to get the max year you were not accessing value correctly if you try like this it will work
Data.aggregate([{ $group: { _id: null, maxBillYear: { $max: "$metadata.billYear" }}} ])
Now the second part of your question to get the max value for the number in single query you can try like this
To get the max bill year from the data
maxBillYear = Data.aggregate([{ $group: { _id: null, maxBillYear: { $max: "$metadata.billYear" }}} ]).first().maxBillYear
To get the max value for the number of bills in a year
Data.aggregate([{ $group: { _id: "$metadata.billYear", maxBillNumber: { $max: "$metadata.billNumber" }}} ])
Yes you can get only max number result on single query
db.collection.aggregate([
{
$group: {
_id: "$metadata.billYear",
maxBillNumber: {
$max: "$metadata.billNumber"
}
}
},
{
$sort: {
_id: -1
}
},
{
$limit: 1
}
])

Related

categraji data by using MongoDb aggregation

Payload in excel sheets that consist of 4 columns i.e Date, status, amount, orderId.You need to structure the data / categorize the columns according to months and in each month orders are categorized as per status.
Umbrella Status:
INTRANSIT - ‘intransit’, ‘at hub’, ‘out for delivery’
RTO - ‘RTO Intransit’, ‘RTO Delivered’
PROCESSING - ‘processing’
For example:
Response should look like: -
May :
1.INTRANSIT
2. RTO
3.PROCESSING
June:
1.INTRANSIT
2. RTO
3.PROCESSING
You can use different aggregation operators provided in MongoDB.For example: -group, facet, Match, unwind, bucket, project, lookup, etc.
I tried it with this:
const pipeline = [{
$facet:
{
"INTRANSIT": [{ $match: { Status: { $in: ['INTRANSIT', 'AT HUB', 'OUT FOR
DELIVERY'] } } }, { $group: { _id: "$Date", numberofbookings: { $sum: 1 } }
}],
"RTO": [{ $match: { Status: { $in: ['RTO INTRANSIT', 'RTO DELIVERED'] } } },
{ $group: { _id: "$Date", numberofbookings: { $sum: 1 } } }],
"PROCESSING": [{ $match: { Status: { $in: ['PROCESSING'] } } }, {
$group: {
_id: date.getMonth("$Date"),
numberofbookings: { $sum: 1 }
}
}]
}
}];
const aggCursor = coll.aggregate(pipeline);

Problem with an aggregated query in mongoDB

I have the following collection in mongodb:
IDcustomer. idServicerequired. ...
001. 13
002. 15
002. 19
002. 10
003. null
From this, i want to get the average number of services required by each customer (in this case, the output should be (1+3+0)/3 = 1.34)
I tried as follows, but in this way, for each customer that has required no service, it is counted 1, as if he had required one service, so the average is higher than expected (in this case it would be (1+3+1)/3=1.67)
first group, check condition if idServicerequired is null then count 0
second $group by null and average count
db.collection.aggregate([
{
$group: {
_id: "$idCustomer",
count: {
$sum: {
$cond: [{ $eq: ["$idServicerequired", null] }, 0, 1]
}
}
}
},
{
$group: {
_id: null,
count: { $avg: "$count" }
}
}
])
Playground

How to count total customers using MongoDB?

Here is the example of the JSON. I want to count the total customers by unique "email_address" and filter by "transactions_status" equal to "S".
Expected output:
{
_id: null,
count: total amount of customers with an unique email address and filtered by status equal S
}
You can try this aggregations pipeline:
Filter by "transactions_status" equal to "S".
Group distinct emails.
Project the count field with the emails's size.
db.collection.aggregate([
{
$match: {
"transaction_info.transaction_status": "S"
}
},
{
$group: {
_id: null,
emails: {
$addToSet: "$payer_info.email_address"
}
}
},
{
$project: {
count: {
$size: "$emails"
}
}
}
]);

Get latest record for each value in a collection field [duplicate]

This question already has answers here:
Mongo DB find all records with highest value depending on a key field
(3 answers)
Closed 3 years ago.
In my collection i have multiple records with same value for "name" field.
I want to retrieve a single record for each name with latest creation date.
Sample aggregation code which i tried.
db.m_collection.aggregate([
{ $group: { _id: { name: "$name" } } }
] )
$sort them by creationDate and then use $last to get most recent date:
db.m_collection.aggregate([
{ $sort: { "creationDate": 1 } },
{ $group: { _id: { name: "$name" }, lastDate: { $last: "$creationDate" } } }
] )
db.m_collection.aggregate([{
$group: {
_id: {
name: "$name"
}
}
},
{
$sort: {
'date': -1 // retrieve data in descending order
}
}
]).limit(10) // number of record you want to find.

How to aggregate data which an array field sum is between two values?

I have two values which are minCount and maxCount.
In my model I have field which is called counts.Something like this.
{
createdAt: date
counts: [ 0,200,100] ==> Sum 300
},
{
createdAt: date
counts: [ 200,500,0] ==> Sum 700
},
{
createdAt: date
counts: [ 0,1100,100] ==> Sum 1200
},
I need to return sum of counts which sum of counts array elements are between minCount and MaxCount.
Exm:
minCount= 400
maxCount= 1300
Return
{
createdAt: date
total: 700
},
{
createdAt: date
total: 1200
},
I
I have createdAt dates between two dates like this in first step of pipe.
Record.aggregate ([
{
$match: {
createdAt: {
$gte: new Date (req.body.startDate),
$lte: new Date (req.body.endDate),
},
},
},
{}, ==> I have to get total counts with condition which I could not here.
])
I am almost new to aggreagate pipeline so please help.
Working example - https://mongoplayground.net/p/I6LOLhTA-yA
db.collection.aggregate([
{
"$project": {
"counts": 1,
"createdAt": 1,
"totalCounts": {
"$sum": "$counts"
}
}
},
{
"$match": {
"totalCounts": {
"$gte": 400,
"$lte": 1300
}
}
}
])