Anda ingin .bulkWrite()
untuk ini. Ini sebenarnya bukan operasi tunggal, jadi Anda ingin mengirimkan beberapa operasi dalam satu permintaan. Pada dasarnya coba tulis pembaruan dengan $set
tempat data memang ada atau $push
data baru yang belum ada:
db.collection.bulkWrite([
{ "updateOne": {
"filter": { "_id": "1", "option.weight": "10" },
"update": {
"$set": { "option.$.price": "30" }
}
}},
{ "updateOne": {
"filter": { "_id": "1", "option.weight": { "$ne": "10" } },
"update": {
"$push": { "option": { "weight": "10", "price": "30" } }
}
}}
])
Kasus positif hanyalah nilainya, dan $ne
"meniadakan" kecocokan kesetaraan, artinya item tersebut tidak ada. Tentu saja posisi $
operator
digunakan dengan $set
di mana itu
Mengingat data hanya satu operasi yang akan benar-benar cocok dan berlaku sebagai pembaruan meskipun dua operasi dikirim dalam "batch".
Jika Anda ingin "upserts" untuk seluruh dokumen juga, maka Anda perlu menambahkan operasi lain di akhir itu. Perhatikan bahwa Anda tidak dapat menerapkan "upsert" sebagai opsi pada salah satu pernyataan lainnya, terutama $ne
karena itu akan membuat dokumen baru di mana item array tidak ada, bukan hanya _id
:
db.collection.bulkWrite([
{ "updateOne": {
"filter": { "_id": "1", "option.weight": "10" },
"update": {
"$set": { "option.$.price": "30" }
}
}},
{ "updateOne": {
"filter": { "_id": "1", "option.weight": { "$ne": "10" } },
"update": {
"$push": { "option": { "weight": "10", "price": "30" } }
}
}},
{ "updateOne": {
"filter": { "_id": 1 },
"update": {
"$setOnInsert": {
"option": [
{ "weight": "10", "price": "30" }
]
}
},
"upsert": true
}}
])
$setOnInsert
adalah bantuan utama di sini selain dari operasi terakhir yang menjadi satu-satunya yang ditandai sebagai "upsert"
. Kombinasi itu memastikan bahwa di mana "dokumen" utama ditemukan, maka tidak ada yang benar-benar terjadi, tetapi ketika tidak ditemukan, item larik baru ditambahkan.
Sebagai catatan tambahan, saya sangat menyarankan untuk menyimpan nilai numerik sebenarnya sebagai numerik daripada string. Tidak hanya menghemat ruang dalam banyak kasus, tetapi juga jauh lebih berguna seperti itu.