Để cập nhật giá trị của trường lồng nhau (nested field / embedded document) trong MongoDB, bạn sử dụng toán tử $set với dot notation (ký pháp dấu chấm).
Cú pháp
db.collection.update(
{ query },
{ $set: { "outerField.innerField": "newValue" } }
)
Ví dụ minh họa
Tạo collection và dữ liệu
> db.updateNestedValueDemo.insertOne({
"CustomerName": "Chris",
"CustomerDetails": {
"CustomerAge": 25,
"CustomerCompanyName": "Google",
"CustomerCityName": "US"
}
});
{ "acknowledged" : true, "insertedId" : ObjectId("5c8fccc4d3c9d04998abf015") }
Xem dữ liệu ban đầu
> db.updateNestedValueDemo.find().pretty();
{
"_id" : ObjectId("5c8fccc4d3c9d04998abf015"),
"CustomerName" : "Chris",
"CustomerDetails" : {
"CustomerAge" : 25,
"CustomerCompanyName" : "Google",
"CustomerCityName" : "US"
}
}
Cập nhật trường lồng nhau: CustomerCompanyName từ "Google" → "Dell"
> db.updateNestedValueDemo.update(
{ },
{ $set: { "CustomerDetails.CustomerCompanyName": "Dell" } }
);
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
Kiểm tra kết quả
> db.updateNestedValueDemo.find().pretty();
{
"_id" : ObjectId("5c8fccc4d3c9d04998abf015"),
"CustomerName" : "Chris",
"CustomerDetails" : {
"CustomerAge" : 25,
"CustomerCompanyName" : "Dell",
"CustomerCityName" : "US"
}
}
Trường CustomerDetails.CustomerCompanyName đã được cập nhật từ "Google" thành "Dell", các trường khác giữ nguyên.
Dot Notation - Ký pháp dấu chấm
MongoDB dùng dấu chấm . để truy cập trường lồng nhau:
"outer.inner"- 1 cấp lồng"outer.middle.inner"- 2 cấp lồng"array.0.field"- truy cập phần tử mảng index 0
Các ví dụ nâng cao
Cập nhật nhiều trường lồng nhau cùng lúc
db.updateNestedValueDemo.update(
{ "CustomerName": "Chris" },
{
$set: {
"CustomerDetails.CustomerCompanyName": "Microsoft",
"CustomerDetails.CustomerCityName": "Seattle",
"CustomerDetails.CustomerAge": 26
}
}
);
Cập nhật phần tử trong mảng lồng nhau
// Giả sử CustomerDetails.Projects là mảng
db.coll.update(
{ _id: ObjectId("...") },
{ $set: { "CustomerDetails.Projects.0.status": "completed" } }
);
Cập nhật có điều kiện (arrayFilters - MongoDB 3.6+)
db.students.updateMany(
{ "grades.course": "math" },
{ $set: { "grades.$[elem].passed": true } },
{ arrayFilters: [{ "elem.score": { $gte: 60 } }] }
);
Lưu ý
- Luôn dùng
$setđể cập nhật một phần document, không replace toàn bộ - Nếu đường dẫn không tồn tại, MongoDB sẽ tạo mới (upsert behavior)
- Tên trường có dấu chấm hoặc ký tự đặc biệt → dùng bracket notation trong code driver, nhưng trong shell dùng string "field.name" vẫn OK
- Kết hợp với
upsert: trueđể tạo document nếu không tồn tại