2013-07-22 9 views
5

Ich hosste eine mongodb-Datenbank für einen Dienst, der Volltextsuche auf einer Sammlung mit 6,8 Millionen Datensätzen unterstützt.MongoDB-Textindexsuche langsam für allgemeine Wörter in großer Tabelle

Der Textindex enthält zehn Felder mit unterschiedlichen Gewichten.

index specification

Die meisten Suchanfragen nehmen weniger als eine Sekunde. Einige Suchen dauern zwei bis drei Sekunden. Einige Suchen dauern jedoch 15 - 60 Sekunden! Die 15-60 Sekunden langen Suchfälle sind für meine Bewerbung inakzeptabel. Ich muss einen Weg finden, diese zu beschleunigen.

Die Suche dauert 15-60 Sekunden, wenn im Index sehr häufige Wörter in der Suchanfrage verwendet werden.

Ich scheint, dass die Textsuchfunktion keine Lazy-Parameter unterstützt. Mein erster Gedanke war, eine Liste der 50 häufigsten Wörter in meinem Textindex zwischenzuspeichern und dann mongodb zu bitten, diese letzten (faul) und obendrauf die gefilterten Ergebnisse zu bewerten, die von den weniger gebräuchlichen Parametern zurückgegeben werden. Hoffentlich sind die Leute immer noch bei mir. Zum Beispiel, ich habe eine Anfrage "Produkte Schokolade", wo Produkte üblich sind und Schokolade ist ungewöhnlich. Ich möchte mongodb bitten, zuerst "Schokolade" zu bewerten und dann diese Ergebnisse mit dem Begriff "Produkte" zu filtern. Kennt jemand einen Weg, dies zu erreichen?

Ich kann das obige Szenario erreichen, indem ich die gängigsten Wörter (d. H. "Produkte") aus der db-Abfrage weggebe und dann den allgemeinen Termfilter auf der Anwendungsseite erneut anwende, nachdem er von db gefundene Datensätze empfangen hat. Es ist vorzuziehen, dass die gesamte Abfragelogik in der Datenbank ausgeführt wird, aber für eine Geschwindigkeitsauszahlung offen für die Verarbeitung auf der Anwendungsseite ist.

Es gibt immer noch einige Löcher in diesem Design. Wenn ein Benutzer nur allgemeine Begriffe sucht, habe ich keine andere Wahl, als die Datenbank mit allen Begriffen zu treffen. Nach vorläufigem Lesen ist es nicht empfehlenswert (oder nicht unterstützt), mehrere Textindizes (mit unterschiedlichen Namen) in derselben Sammlung zu haben. Mein Plan besteht darin, zwei identische Tabellen mit jeweils 6,8 Millionen Einträgen mit unterschiedlichen Indizes zu erstellen - einen für häufige Wörter und einen für ungewöhnliche Wörter. Das fühlt sich klebrig und klobig an, aber ich bin bereit, dies für eine Geschwindigkeitssteigerung zu tun.

Hat jemand irgendeinen Einblick und/oder Ratschläge, wie man dieses System beschleunigt. Ich möchte so viel wie möglich in der Datenbank verarbeiten, um es schnell zu halten. Ich bin mir sicher, dass mein kleiner 6.8M Rekordtisch nicht der größte ist, den mongodb gesehen hat. Vielen Dank!

+0

Es ist jetzt 2018 (5 Jahre später), und mongodb hat immer noch das exakt gleiche Problem :( – Nico

+1

deswegen gepaart mit Mongo's signifikanter Performance durch die Umsetzung dieses, durch die wir den Einsatz von Mongo so bestimmt haben, war nicht eine "unterstützte" oder "beabsichtigte" primäre Verwendung, haben wir beschlossen, Mongo insgesamt zu entziehen. Entschuldigung für das kalte Wasser. – kmehta

Antwort

4

Nun, ich habe mich mit diesen Leistungsproblemen beschäftigt, indem ich die MongoDB-Volltextsuche für die Suche im OR-basierten Format zugelassen habe. Ich priorisiere meine Ergebnisse, indem ich die Gewichte meiner indizierten Felder verfeinere und nur nach Rang sortiert habe. Ich bekomme mehr Ergebnisse als gewünscht, aber das ist kein großes Problem, da meine gewichteten Ergebnisse, die oben angezeigt werden, höchstwahrscheinlich verbraucht werden, bevor mein Benutzer am unteren Rand zu weniger relevanten Ergebnissen kommt.

Wenn jemand mit der MongoDB-Textsuchleistung nur mit AND-Suche zu kämpfen hat, wechseln Sie einfach zurück zu OR und kontrollieren Sie Ihre Ergebnisse mit Gewichten. Es führt Sprünge besser aus.

hth

+3

Genau. Wenn Sie Suchbegriffe in Anführungszeichen verwenden (was ich denke, was Sie mit UND-Format meinen), MongoDB Text Bei der Suche wird zuerst der Textindex über Wortstammwörter verwendet und dann jedes Dokument überprüft, um sicherzustellen, dass (a) beide Wörter vorhanden sind und (b) die nicht gestaffelte Version der Wörter mit den zitierten Termen identisch ist, die Sie übergeben haben viel weniger performant als die andere Option (ohne die Begriffe zu zitieren), in der der Textindex verwendet wird und kein zweites Dokument durchlaufen wird Achten Sie auf Ranking-Ergebnisse mit beiden Wörtern vorhanden Ergebnisse mit nur einem. – Amalia

0

Dies ist genau das gleiche Problem wie $ im Vergleich zu $ ​​all in. $ all verwendet nur den Index für das erste Schlüsselwort im Array. Ich glaube, dass Sie das gleiche Problem hier sehen, warum das OR a.k.a.IN für Sie arbeitet.