MongoDB
 sql >> Teknologi Basis Data >  >> NoSQL >> MongoDB

MongoDB:sub-dokumen tambahan

Tidak, sebenarnya tidak ada solusi yang lebih baik untuk ini, jadi mungkin dengan penjelasan.

Misalkan Anda memiliki dokumen di tempat yang memiliki struktur seperti yang Anda tunjukkan:

{ 
  "name": "foo", 
  "bars": [{ 
       "name": "qux", 
       "somefield": 1 
  }] 
}

Jika Anda melakukan pembaruan seperti ini

db.foo.update(
    { "name": "foo", "bars.name": "qux" },
    { "$set": { "bars.$.somefield": 2 } },
    { "upsert": true }
)

Maka semuanya baik-baik saja karena dokumen yang cocok ditemukan. Tetapi jika Anda mengubah nilai "bars.name":

db.foo.update(
    { "name": "foo", "bars.name": "xyz" },
    { "$set": { "bars.$.somefield": 2 } },
    { "upsert": true }
)

Maka Anda akan mendapatkan kegagalan. Satu-satunya hal yang benar-benar berubah di sini adalah bahwa di MongoDB 2.6 dan di atasnya kesalahannya sedikit lebih ringkas:

WriteResult({
    "nMatched" : 0,
    "nUpserted" : 0,
    "nModified" : 0,
    "writeError" : {
        "code" : 16836,
        "errmsg" : "The positional operator did not find the match needed from the query. Unexpanded update: bars.$.somefield"
    }
})

Itu lebih baik dalam beberapa hal, tetapi Anda benar-benar tidak ingin "mengganggu". Yang ingin Anda lakukan adalah menambahkan elemen ke larik di mana "nama" saat ini tidak ada.

Jadi yang sebenarnya Anda inginkan adalah "hasil" dari upaya pembaruan tanpa tanda "upsert" untuk melihat apakah ada dokumen yang terpengaruh:

db.foo.update(
    { "name": "foo", "bars.name": "xyz" },
    { "$set": { "bars.$.somefield": 2 } }
)

Mengalah sebagai tanggapan:

WriteResult({ "nMatched" : 0, "nUpserted" : 0, "nModified" : 0 })

Jadi ketika dokumen yang dimodifikasi adalah 0 maka Anda tahu Anda ingin mengeluarkan pembaruan berikut:

db.foo.update(
    { "name": "foo" },
    { "$push": { "bars": {
        "name": "xyz",
        "somefield": 2
    }}
)

Benar-benar tidak ada cara lain untuk melakukan apa yang Anda inginkan. Karena penambahan pada larik tidak sepenuhnya merupakan jenis operasi "set", Anda tidak dapat menggunakan $addToSet digabungkan dengan fungsi "pembaruan massal" di sana, sehingga Anda dapat "mengurutkan" permintaan pembaruan Anda.

Dalam hal ini sepertinya Anda perlu memeriksa hasilnya, atau menerima membaca seluruh dokumen dan memeriksa apakah akan memperbarui atau menyisipkan elemen array baru dalam kode.



  1. Redis
  2.   
  3. MongoDB
  4.   
  5. Memcached
  6.   
  7. HBase
  8.   
  9. CouchDB
  1. MongoDB untuk Setiap()

  2. Cara menggunakan kembali koneksi mongodb melalui Promise

  3. MongoDB:Tidak dapat mengkanonikalisasi kueri:Proyeksi BadValue tidak dapat memiliki campuran penyertaan dan pengecualian

  4. Cara Menggabungkan Dokumen saat Mengimpor File ke MongoDB

  5. MongoDB vs MySQL NoSQL - Mengapa Mongo Lebih Baik