У меня есть набор вложенных объектов mongodb, поэтому моя коллекция:
{
"_id":17846384es,
"company_name":"company1",
"company_location":"city1",
"phone":"xxxxx",
"open_time":"xxx",
"products":[
{
"product_id":"123785",
"product_name":"product1",
"user_votes":[
{
"user_id":1,
"vote":1
},
{
"user_id":2,
"vote":2
}
]
},
{
"product_id":"98765",
"product_name":"product2",
"user_votes":[
{
"user_id":5,
"vote":3
},
{
"user_id":3,
"vote":3
}
]
}
]
}
Я использовал некоторые операции, такие как сортировка и суммирование в этой части документов, поэтому я использовал
db.products.aggregate([
{ $unwind: "$products" },
{ $project: {
company_name: 1,
products: {
product_id: 1,
product_name: 1,
user_votes: 1,
votes: { $sum: "$products.user_votes.vote" }
}
} },
{ $sort: { totalVotes: -1 } },
{
$group: {
_id: "$_id",
company_name: { $first: "$company_name" },
products: { $push: "$products" }
}
}
])
чтобы получить этот результат:
{
"_id":17846384es,
"company_name":"company1",
"products":[
{
"product_id":"98765",
"product_name":"product2",
"user_votes":[
{
"user_id":5,
"vote":3
},
{
"user_id":3,
"vote":3
}
]
"votes":6
},
{
"product_id":"123785",
"product_name":"product1",
"user_votes":[
{
"user_id":1,
"vote":1
},
{
"user_id":2,
"vote":2
}
],
"votes":3
}
]
}
но если документ продукта не существует, у меня будет пустой результат. Я хочу получить результат с информацией о компании, даже если документ о продукте не существует.
Во-первых, вы можете использовать "preserveNullAndEmptyArrays"
сохранить компанию, у которой нет ассортимента продукции.
Приведенный ниже запрос должен выводить названия компаний, даже если у них нет массива products.
Я думаю, что вы пытаетесь суммировать голоса и сортировать массив продуктов, чтобы получить наибольшее количество продуктов в качестве первого элемента в массиве. Приведенный ниже запрос должен дать результат.
db.product.aggregate([
{ $unwind: { path : "$products", preserveNullAndEmptyArrays : true }},
{ $project: {
company_name: 1,
products : { $ifNull : ["$products", "0"]}}
},
{ $project: {
company_name: 1,
products: {
product_id: 1,
product_name: 1,
user_votes: 1,
votes: { $sum: "$products.user_votes.vote" }
}
} },
{ $sort: { "products.votes": -1 } },
{
$group: {
_id: "$_id",
company_name: { $first: "$company_name" },
products: { $push: "$products" }
}
},
]);
В случае, если вы хотите сохранить компании, у которых нет продукта в конце. Вы можете добавить эту дополнительную сортировку как последний конвейер в приведенном выше запросе.
{ $sort: { "products.votes": -1 } },
Продукция компаний, у которых нет товарного массива, будет выглядеть так:
{
"_id" : ObjectId("57f2bd50dd4752c20947fd03"),
"company_name" : "company2",
"products" : [
{
"votes" : 0
}
]
}
Других решений пока нет …