【发布时间】:2018-12-19 22:28:54
【问题描述】:
我正在尝试结合使用 $group 和 $project 运算符(除非有更好的选择)来生成两个值。
考虑如下所示的文档数据结构:
[
{
_id: 1,
openBalance: 22,
customerResponsible: true
},
{
_id: 2,
openBalance: 16,
customerResponsible: false
},
{
_id: 3,
openBalance: 10,
customerResponsible: true
},
{
_id: 4,
openBalance: 20,
customerResponsible: false
},
]
我要做的是输出一个值为customerOpenBalance 的文档,它代表“customerResponsible”为true 的文档的总openBalance。还有一个值agencyOpenBalance,它表示“customerResponsible”设置为false的总openBalance。
现在,我可以在$group 阶段做到这一点:
"customerResponsibleOpenBalance" : { "$sum" : { "$cond" : [ "$customerResponsibile", 1, 0 ] }},
然后在稍后的$project 阶段执行此操作:
"customerResponsibleOpenBalance" : { "$sum": "$customerResponsibleOpenBalance" }
但这给我的是instances 中的$sum,而不是我真正想要的,即openBalance 中的值 的总和,其中,对于customerResponsibleOpenBalance 的情况,我定位的布尔值 customerResponsible 是 true。
如何调整此聚合以获取在$openBalance 中找到的值的$sum,而不是实例的$sum?
我的完整聚合管道如下所示(关键阶段是第 6 阶段的 $group 和第 18 阶段的 $project:
db.transactions.aggregate(
// Pipeline
[
// Stage 1
{
$match: {
"openBalance": {
"$ne": 0.0
}
}
},
// Stage 2
{
$lookup: {
"from": "customers",
"localField": "customer.id",
"foreignField": "_id",
"as": "customer"
}
},
// Stage 3
{
$unwind: {
"path": "$customer"
}
},
// Stage 4
{
$lookup: {
"from": "visits",
"localField": "visit.id",
"foreignField": "_id",
"as": "visit"
}
},
// Stage 5
{
$unwind: {
"path": "$visit"
}
},
// Stage 6
{
$group: {
"_id": "$customer._id",
"submissions": {
"$push": "$submissions"
},
"staffMember": {
"$first": "$staffMember.id"
},
"visit": {
"$first": "$visit"
},
"openBalance": {
"$sum": "$openBalance"
},
"customerResponsibleOpenBalance": {
"$sum": {
"$cond": ["$visit.customerResponsibility", 1, 0]
}
},
"agencyResponsibleOpenBalance": {
"$sum": {
"$cond": ["$visit.customerResponsibility", 0, 1]
}
},
"openClaims": {
"$sum": {
"$cond": {
"if": {
"$gt": ["$submissions.0.responses.balance", 0.0]
},
"then": 1.0,
"else": 0.0
}
}
}
}
},
// Stage 7
{
$addFields: {
"payerInfo": "$submissions.0.details.agency._id"
}
},
// Stage 8
{
$lookup: {
"from": "agencies",
"localField": "submissions.0.details.agency._id",
"foreignField": "_id",
"as": "agency"
}
},
// Stage 9
{
$unwind: {
"path": "$agency"
}
},
// Stage 10
{
$addFields: {
"claimSupervisor": "$agency.claims.supervisor"
}
},
// Stage 11
{
$lookup: {
"from": "staffmembers",
"localField": "claimSupervisor",
"foreignField": "_id",
"as": "claimSupervisor"
}
},
// Stage 12
{
$unwind: {
"path": "$claimSupervisor"
}
},
// Stage 13
{
$lookup: {
"from": "customers",
"localField": "_id",
"foreignField": "_id",
"as": "customer"
}
},
// Stage 14
{
$unwind: {
"path": "$customer"
}
},
// Stage 15
{
$lookup: {
"from": "locales",
"localField": "customer.locale",
"foreignField": "_id",
"as": "locale"
}
},
// Stage 16
{
$unwind: {
"path": "$locale"
}
},
// Stage 17
{
$lookup: {
"from": "agencies",
"localField": "agencies",
"foreignField": "_id",
"as": "agencies"
}
},
// Stage 18
{
$project: {
"customer": {
"_id": 1.0,
"name": 1.0
},
"agency": {
"_id": 1.0,
"name": 1.0,
"transactionType": 1.0
},
"visit": {
"_id": 1.0,
"customerResponsibility": 1.0
},
"openBalance": 1.0,
"openClaims": 1.0,
"customerResponsibleOpenBalance": {
"$sum": "$customerResponsibleOpenBalance"
},
"agencyResponsibleOpenBalance": {
"$sum": "$agencyResponsibleOpenBalance"
},
"locale": {
"_id": 1.0,
"name": 1.0
},
"firstSubmission": {
"$arrayElemAt": ["$submissions", 0.0]
},
"lastSubmission": {
"$arrayElemAt": ["$submissions", -1.0]
},
"claimSupervisor": {
"_id": 1.0,
"name": 1.0
}
}
},
// Stage 19
{
$unwind: {
"path": "$firstSubmission"
}
},
// Stage 20
{
$unwind: {
"path": "$lastSubmission"
}
},
// Stage 21
{
$project: {
"firstSubmission": {
"details": 0.0,
"responses": 0.0
},
"lastSubmission": {
"details": 0.0,
"responses": 0.0
}
}
},
],
);
【问题讨论】:
-
我有一种感觉,有一大堆事情不太对劲。如果您可以发布一些具有所需输出的匹配示例数据,我相信我们可以为您提供正确的结果。
标签: javascript mongodb aggregation-framework