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

Möglichkeit, die Speichernutzung durch Mungo bei der Abfrage zu verringern

Standard-Mungo .find() Natürlich werden alle Ergebnisse als "Array" zurückgegeben, sodass bei großen Ergebnissen immer Speicher verwendet wird, sodass dies die "Stream" -Schnittstelle verlässt.

Das grundlegende Problem hierbei ist, dass Sie einen Stream verwenden Schnittstelle ( da diese vom grundlegenden Knotenstrom erbt ) wird jedes Datenereignis "ausgelöst" und der zugehörige Ereignishandler wird kontinuierlich ausgeführt.

Das bedeutet, dass selbst bei einem "Stream" Ihre nachfolgenden Aktionen im Event-Handler "stapeln", zumindest viel Speicher verbrauchen und möglicherweise den Call-Stack auffressen, wenn dort weitere asynchrone Prozesse abgefeuert werden.

Das Beste, was Sie tun können, ist, die Aktionen in Ihrer Stream-Verarbeitung zu "begrenzen". Dies ist so einfach wie der Aufruf von .pause() Methode:

var stream = model.find().stream();   // however you call

stream.on("data",function() {
    // call pause on entry
    stream.pause();

    // do processing
    stream.resume();            // then resume when done
});

Also .pause() stoppt die Ereignisse im Stream, die ausgegeben werden, und dies ermöglicht, dass die Aktionen in Ihrem Ereignishandler abgeschlossen werden, bevor sie fortfahren, sodass sie nicht alle gleichzeitig kommen.

Wenn Ihr Handhabungscode vollständig ist, rufen Sie .resume() auf , entweder direkt innerhalb des Blocks, wie hier gezeigt, oder innerhalb des Callback-Blocks einer asynchronen Aktion, die innerhalb des Blocks ausgeführt wird. Beachten Sie, dass die gleichen Regeln für asynchrone Aktionen gelten und dass „all“ den Abschluss signalisieren muss, bevor Sie „resume“ aufrufen sollten.

Es gibt auch andere Optimierungen, die angewendet werden können, und Sie könnten gut daran tun, nach verfügbaren Modulen für "Warteschlangenverarbeitung" oder "asynchrone Flusssteuerung" zu suchen, die Ihnen dabei helfen, mit einer parallelen Ausführung davon mehr Leistung zu erzielen.

Aber denken Sie im Grunde an .pause() dann verarbeiten und .resume() um weiterhin viel Speicher in Ihrer Verarbeitung zu vermeiden.

Achten Sie auch auf Ihre "Ausgaben" und versuchen Sie auf ähnliche Weise, wieder einen "Stream" zu verwenden, wenn Sie etwas für eine Antwort aufbauen. All dies ist umsonst, wenn Ihre Arbeit nur darin besteht, eine weitere Variable im Speicher aufzubauen, daher ist es hilfreich, sich dessen bewusst zu sein.