MongoDB
 sql >> Datenbank >  >> NoSQL >> MongoDB

Wie konstruiere ich eine Abfrage, um ein verschachteltes Array-Dokument in Mongo zu aktualisieren?

Der Positionsoperator funktioniert nicht auf der Anzahl von Ebenen, auf denen Sie versuchen, ihn zum Laufen zu bringen ( https://jira.mongodb.org/browse/SERVER-831?focusedCommentId=22438&page=com.atlassian.jira.plugin.system. issuetabpanels%3Acomment-tabpanel ) mit menus.$.items.$.name und selbst wenn dies der Fall wäre, hätte der MongoDB-Abfrageparser keine Ahnung, was der andere $ ist stammt aus find des update .

Sie müssen die Elemente aus dem Schema herausziehen, dieses separat aktualisieren und dann das Stammdokument aktualisieren.

Eine gute Möglichkeit zu beurteilen, wann Abfragen separat durchgeführt werden sollten, besteht darin, zu glauben, dass jedes Menü wie eine separate Entität (oder Tabelle in einer relationalen Datenbank) klingt, sodass Sie wahrscheinlich daran arbeiten sollten, diese Entitäten (oder Tabellen in einem relationalen Modell) separat zu aktualisieren die übergeordnete Entität (Tabelle).

Zuerst würden Sie also das Hauptstammdokument herausholen. Scrollen Sie auf der Client-Seite durch die Menüs und dann $set dieses spezielle Menü auf das gesamte Element, das Sie auf der Client-Seite erstellen.

Bearbeiten

Die Art und Weise, wie ich mir diese Arbeit auf der Client-Seite vorstelle, ist (in Pseudo-Code, da mein Java ein wenig eingerostet ist), indem ich zuerst dieses Dokument in einer aktiven Datensatzart erhalte:

doc = db.col.find({ "_id" : { "$oid" : "506e9e54a4e8f51423679428"} , 
    "menus._id" : { "$oid" : "506e9e5aa4e8f51423679429"}});

Dann würden Sie das Dokument durchlaufen und Ihre Werte zuweisen:

foreach(doc.menus as menu_key => menu){
    foreach(menu['items'] as key => item){
        if(item._id ==  { "$oid" : "506e9f07a4e8f5142367942f"}){
            doc.menus[menu_key][key][name] = "xcvxc66666"
        }
    }
}

Und dann speichern Sie das Dokument einfach, nachdem alle Änderungen übernommen wurden:

db.col.save(doc);

Dies ist natürlich nur eine Möglichkeit, dies zu tun, und verwendet auf diese Weise das Activen-Record-Paradigma, das mir persönlich gefällt. Bei dieser Idee würden Sie die Suche mit allem anderen kombinieren, was Sie am Dokument ändern müssen, es auf der Client-Seite aufbauen und dann alles als eine einzige Abfrage an Ihre Datenbank senden.