Không thể cập nhật trực tiếp từ aggregation pipeline (trước MongoDB 4.2). Cách phổ biến: dùng aggregation để tìm điều kiện, rồi dùng update() với arrayFilters.
Tạo collection:
> db.demo376.insertOne({
"id" :101,
"details" : [
{ "Name":"Chris", "Age":21, "Score":45 },
{ "Name":"David", "Age":23, "Score":67 },
{ "Name":"Bob", "Age":20, "Score":54 }
]
});
{ "acknowledged" : true, "insertedId" : ObjectId("5e5a71b92ae06a1609a00b0d") }
Xem dữ liệu:
> db.demo376.find().pretty();
{ "_id" : ObjectId("5e5a71b92ae06a1609a00b0d"), "id" : 101, "details" : [ { "Name" : "Chris", "Age" : 21, "Score" : 45 }, { "Name" : "David", "Age" : 23, "Score" : 67 }, { "Name" : "Bob", "Age" : 20, "Score" : 54 } ] }
Cập nhật: tăng Age lên 3 cho phần tử có Age=21 VÀ Score>40 (dùng arrayFilters):
> db.demo376.update(
{"id" :101},
{$inc:{"details.$[d].Age":3}},
{arrayFilters: [ {$and:[{"d.Age": 21},{"d.Score": {$gt:40}} ]}] }
)
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
Kết quả (Chris Age: 21 → 24):
> db.demo376.find().pretty();
Giải thích arrayFilters:
dlà biến đại diện cho mỗi phần tử mảng details{$and:[{"d.Age": 21},{"d.Score": {$gt:40}}]}: điều kiện lọc phần tửdetails.$[d].Age: cập nhật trường Age của các phần tử thỏa mãn filter
MongoDB 4.2+: Hỗ trợ updateMany với pipeline aggregation (dùng $set, $unset...).