Je suis nouveau sur Mongo Db et j'apprécierais de l'aide avec cette requête. J'ai passé en revue les articles ici ces derniers jours en me déchirant les cheveux pour voir si je pouvais trouver quoi que ce soit lié à ma requête, mais sans chance.
J'ai une collection avec des documents de structure similaire à ci-dessous:
_id: xyz
Movieid: 123
MovieName: Titanic
ReleaseDate: 2000-01-01
_id: uvw
Movieid: 456
MovieName: Titanic II
ReleaseDate: 2018-01-01
_id: pqr
Movieid: 789
MovieName: Titanic III
ReleaseDate:
Je voudrais obtenir la sortie en tant que nombre de films totaux, de films avec date de sortie et de films sans date de sortie dans 3 colonnes séparées comme ci-dessous:
Total | Released | UnReleased
3 | 2 | 1
J'ai pu écrire des requêtes individuelles pour exécuter les décomptes, mais je ne parviens pas à consolider tout cela en une seule requête. L'objectif final est de créer une vue produisant ces comptes en sortie. J'ai essayé d'utiliser des opérateurs tels que $ et, mais je n'arrive pas à faire fonctionner la requête comme souhaité .... c'est pour autant que j'ai:
db.getCollection("Movies").aggregate({
"$and": [
{ "$match": { "ReleaseDate": { "$exists": true } }},
{ "$count": "Total" },
{ "$match": { "ReleaseDate": { "$exists": true, "$nin": [""] } }},
{ "$count": "Released" },
{ "$match": { "ReleaseDate": { "$exists": true, "$in": [""] } }},
{ "$count": "Unreleased" }
]
})
Vous pouvez essayer ci-dessous $facet
agrégation
$count
l'agrégation vous donnera toujours les chiffres pour une seule correspondance ( $match
) condition. Vous devez donc diviser votre compte en plusieurs sections et c'est ce que le $facet
fournit par processus plusieurs pipelines d'agrégation en une seule étape sur le même ensemble de documents d'entrée.
db.collection.aggregate([
{ "$facet": {
"Total": [
{ "$match" : { "ReleaseDate": { "$exists": true }}},
{ "$count": "Total" },
],
"Released": [
{ "$match" : {"ReleaseDate": { "$exists": true, "$nin": [""] }}},
{ "$count": "Released" }
],
"Unreleased": [
{ "$match" : {"ReleaseDate": { "$exists": true, "$in": [""] }}},
{ "$count": "Unreleased" }
]
}},
{ "$project": {
"Total": { "$arrayElemAt": ["$Total.Total", 0] },
"Released": { "$arrayElemAt": ["$Released.Released", 0] },
"Unreleased": { "$arrayElemAt": ["$Unreleased.Unreleased", 0] }
}}
])
[{
"Total": 3,
"Released": 2,
"Unreleased": 1
}]
Vous pouvez utiliser l'agrégation ci-dessous.
$gt > null
- pour vérifier si le champ existe ou non dans les expressions d'agrégation.
$cond
avec $sum
pour sortir 0 et 1 en fonction du filtre de date de sortie.
$add
pour ajouter le nombre publié et non publié au total de sortie.
db.Movies.aggregate([
{"$group":{
"_id":null,
"Unreleased":{"$sum":{"$cond":[{"$and":[{"$gt":["$ReleaseDate",null]},{"$ne":["$ReleaseDate",""]}]},0,1]}},
"Released":{"$sum":{"$cond":[{"$and":[{"$gt":["$ReleaseDate",null]},{"$ne":["$ReleaseDate",""]}]},1,0]}}
}},
{"$addFields":{"Total":{"$add":["$Unreleased","$Released"]}}}
])
db.Movies.aggregate(
// Pipeline
[
// Stage 1
{
$group: {
_id: null,
Total: {
$sum: 1
},
docs: {
$Push: '$$ROOT'
}
}
},
// Stage 2
{
$project: {
_id: 0,
Total: 1,
Released: {
$filter: {
input: "$docs",
as: "doc",
cond: {
$ne: ["$$doc.ReleaseDate", ""]
}
}
},
Unreleased: {
$filter: {
input: "$docs",
as: "doc",
cond: {
$eq: ["$$doc.ReleaseDate", ""]
}
}
},
}
},
// Stage 3
{
$project: {
Total: 1,
Released: {
$size: '$Released'
},
UnReleased: {
$size: '$Unreleased'
}
}
},
]
);