基于嵌套数组条件的mongoDB更新
我在基于嵌套数组条件的mongoDB更新,mongodb,Mongodb,我在users集合中有以下结构: [ { "name": "Ivan", "payments": [ {"date": new Date("2019-01-01"), "details": [{"payment_system": "A", "spent": 95}, {"payment_system": "B", "spent": 123}]}, {"da
users
集合中有以下结构:
[
{ "name": "Ivan",
"payments": [
{"date": new Date("2019-01-01"), "details": [{"payment_system": "A", "spent": 95},
{"payment_system": "B", "spent": 123}]},
{"date": new Date("2019-01-03"), "details": [{"payment_system": "A", "spent": 12},
{"payment_system": "B", "spent": 11}]}]},
{ "name": "Mark",
"payments": [
{"date": new Date("2019-01-01"), "details": [{"payment_system": "D", "spent": 456},
{"payment_system": "B", "spent": 123}]},
{"date": new Date("2019-01-02"), "details": [{"payment_system": "A", "spent": 98},
{"payment_system": "C", "spent": 4}]}]}
]
在特定的支付系统中,在特定的日期范围内花费超过100英镑的用户是否可以添加一个字段?
我尝试了updateMany
,但不知道如何基于payment\u system
字段过滤“details”数组元素
对于(“A”、“C”)中的支付系统,日期>=“2019-01-02”,花费总额>=100
更新应返回
[
{ "name": "Ivan", ...},
{ "name": "Mark", "filter_passed": true, ... }
]
这个:
db.collection.aggregate([
{
$set: {
payments: {
$filter: {
input: "$payments",
cond: { $gte: ["$$this.date", new Date("2019-01-02")] }
}
}
}
},
{
$set: {
spent_total: {
$reduce: {
input: "$payments.details.spent",
initialValue: [],
in: { $concatArrays: ["$$value", "$$this"] }
}
}
}
},
{ $set: { spent_total: { $sum: "$spent_total" } } },
{ $match: { "spent_total": { $gte: 100 } } }
])
蒙戈
更新:
按支付系统过滤的时间稍长。您必须$unwind
和$group
:
db.collection.aggregate([
{
$set: {
payments: {
$filter: {
input: "$payments",
cond: { $gte: ["$$this.date", new Date("2019-01-02")] }
}
}
}
},
{ $unwind: "$payments" },
{
$set: {
"payments.details": {
$filter: {
input: "$payments.details",
cond: { $in: ["$$this.payment_system", ["A", "C"]] }
},
},
}
},
{
$group: {
_id: { _id: "$_id", name: "$name", },
payments: { $push: "$payments" }
}
},
{
$set: {
spent_total: {
$reduce: {
input: "$payments.details.spent",
initialValue: [],
in: { $concatArrays: ["$$value", "$$this"] }
}
}
}
},
{ $set: { spent_total: { $sum: "$spent_total" } } },
{ $match: { "spent_total": { $gte: 100 } } },
{ // just some cosmetic
$project: {
_id: "$_id._id",
name: "$_id.name",
payments: 1
}
}
])
您不能像db.collection.updateName({},[])
那样更新集合,因为它包含$unwind
和$group
。
但是,您可以进行$lookup
或将整个结果保存到新集合中
如果您需要对每个支付系统
分别进行汇总,请尝试:
db.collection.aggregate([
{
$set: {
payments: {
$filter: {
input: "$payments",
cond: { $gte: ["$$this.date", new Date("2019-01-01")] }
}
}
}
},
{ $unwind: "$payments" },
{
$set: {
"payments.details": {
$filter: {
input: "$payments.details",
cond: { $in: ["$$this.payment_system", ["A", "B","C"]] }
},
},
}
},
{ $unwind: "$payments.details" },
{
$group: {
_id: {
_id: "$_id",
name: "$name",
payments: "$payments.details.payment_system"
},
spent_total: { $sum: "$payments.details.spent" }
}
},
{ $match: { "spent_total": { $gte: 100 } } },
{
$project: {
_id: "$_id._id",
name: "$_id.name",
payments: "$_id.payments",
spent_total: 1
}
}
])
那么总是在一个特定的日期和特定的支付系统?支付系统是否会在日期的详细信息中出现不止一次?@Tomslabaert当然,这是可能的您想更新文档还是只想检索?@SuleymanSah理想情况下会更新,但至少检索也很好花费的总数是否意味着详细信息数组中花费的总和?谢谢您的回答!是否有任何方法可以通过支付系统
过滤支付。详细信息
,然后求和?请记住,所有支付系统(即本例中的A和C)的汇总和