So indizieren Sie dynamische Attribute in MongoDB


8

Ich habe folgende Art von Daten (etwas vereinfacht von meinem realen Fall) in MongoDB:

{
    "name":"some name",
    "attrs":[
        {"n":"subject","v":"Some subject"},
        {"n":"description","v":"Some great description"},
        {"n":"comments","v":"Comments are here!"},
        ]
}

Das attrs-Array ist ein Container für dynamische Attribute, dh ich weiß vorher nicht, welche Attribute dort abgelegt werden. n steht für Name und v steht für Wert.

Das MongoDB In Action-Buch beschreibt dies als eine Lösung für dynamische Attribute für den Fall, dass die Attribute vollständig vorhersehbar sind. Es wird auch beschrieben, dass Sie es wie folgt indizieren können:

db.mycollection.ensureIndex({"attrs.n":1, "attrs.v":1})

Abfragen können dann folgendermaßen durchgeführt werden:

db.mycollection.find({attrs: {$elemMatch: {n: "subject", v: "Some subject"}}})

Wenn ich das teste, bekomme ich eine sehr schlechte Leistung. Ich habe mit mycollection mit 2 Millionen Dokumenten getestet und ohne Index scheint die Leistung besser zu sein.

Die Frage lautet also: Gibt es eine Möglichkeit, diese Art der dynamischen Attributeinstellung zu indizieren, damit die Indizierung eine gute Leistung erbringt? In meinem Fall ist es nicht möglich, nur Schlüssel wie "Betreff" und "Beschreibung" zu haben und sie alle zu indizieren ...

Antworten:


5

Ich habe diese Frage auch (in etwas erweiterter Form) auf der Mailingliste der Mongodb-Benutzer gestellt , wo ich eine Antwort bekam. Lesen Sie von dort aus, um weitere Informationen zu erhalten. Die kurze Antwort lautet, dass die in der Frage verwendete Strategie gut funktionieren sollte, aber es gibt ein Problem , das sie sehr ineffizient macht. Hoffentlich wird das Problem bald behoben.

In meinem Fall muss ich nur nach genauen Übereinstimmungen für das Tupel {n, v} fragen, damit ich einen Multikey-Index erstellen kann:

db.mycollection.ensureIndex({"attrs":1})

und lassen Sie sie wie folgt abfragen:

db.mycollection.find({"attrs": {n: "subject", v: "Some subject"}})

Das funktioniert super und nutzt den Index sehr effektiv.


0

Die gleiche Frage wurde hier gestellt . Ab der Version 4.2 von MongoDB kündigten sie Platzhalterindizes an. Hier ist ein Beispiel:

db.myCollection.createIndex( { "subdocument.$**": 1 } );
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.