REDIGER
Den detalje, der manglede i spørgsmålet, var, at det påkrævede felt til opdatering faktisk var i et underdokument . Dette ændrer svaret betydeligt:
Dette er en begrænsning af, hvad du kan evt gøre med at opdatere array-elementer. Og dette er tydeligt forklaret i dokumentationen . Mest i dette afsnit:
Så her er sagen. Forsøger at opdatere alle af array-elementerne i en enkelt sætning som denne ikke arbejde. For at gøre dette skal du gøre følgende.
db.warehouses.find({ "items.qty": { "$gt": 0 } }).forEach(function(doc) {
doc.items.forEach(function(item) {
item.qty = 0;
});
db.warehouses.update({ "_id": doc._id }, doc );
})
Hvilket dybest set er måden at opdatere hver array element.
multi indstilling i .update()
betyder på tværs af flere "dokumenter". Det kan ikke anvendes på flere elementer i et array. Så i øjeblikket er den bedste mulighed at erstatte det hele. Eller i dette tilfælde kan vi lige så godt erstatte hele dokument, da vi alligevel skal gøre det.
For rigtig massedata, brug db.eval() . Men læs venligst dokumentationen først:
db.eval(function() {
db.warehouses.find({ "items.qty": { "$gt": 0 } }).forEach(function(doc) {
doc.items.forEach(function(item) {
item.qty = 0;
});
db.warehouses.update({ "_id": doc._id }, doc );
});
})
Opdaterer alle elementerne i et array på tværs af helheden indsamling er ikke enkel.
Original
Stort set præcis hvad fejlen siger. For at bruge en positionsoperator skal du matche noget først. Som i:
db.warehouses.update(
// query
{
_id:ObjectId('5322f07e139cdd7e31178b78'),
"items.qty": { "$gt": 0 }
},
// update
{
$set:{"items.$.qty":0}
},
// options
{
"multi" : true,
"upsert" : true
}
);
Så hvor kampen tilstand finner positionen af de varer, der er mindre end 0 derefter det indeks videregives til positionsoperatøren.
P.S :Når muti er sandt det betyder, at den opdaterer hver dokument. Lad det være false
hvis du kun mener én . Hvilket er standard.