Postgres-Caches / Puffer sehen und löschen?

88

Manchmal führe ich eine Postgres-Abfrage aus, die 30 Sekunden dauert. Dann führe ich sofort dieselbe Abfrage aus und es dauert 2 Sekunden. Es scheint, dass Postgres eine Art Caching hat. Kann ich irgendwie sehen, was dieser Cache enthält? Kann ich erzwingen, dass alle Caches zu Optimierungszwecken gelöscht werden?

Hinweis: Ich suche grundsätzlich nach einer Postgres-Version des folgenden SQL Server-Befehls:


DBCC FREEPROCCACHE
DBCC DROPCLEANBUFFERS

Ich würde aber auch gerne wissen, wie man sieht, was tatsächlich in diesem Puffer enthalten ist.

Vielen Dank für jede Hilfe.

Benutzer1
quelle

Antworten:

59

Mit dem Modul pg_buffercache können Sie sehen, was sich im PostgreSQL-Puffercache befindet. Ich habe eine Präsentation mit dem Titel " Inside the PostgreSQL Buffer Cache" durchgeführt " erstellt, in der erklärt wird, was Sie sehen, und ich zeige einige kompliziertere Abfragen, um die damit verbundenen Informationen zu interpretieren.

Auf einigen Systemen ist es auch möglich, den Betriebssystem-Cache zu betrachten. Ein etwas grobes Beispiel finden Sie in pg_osmem.py .

Es gibt keine Möglichkeit, die Caches einfach zu löschen. Unter Linux können Sie den Datenbankserver stoppen und den Betriebssystem-Cache mithilfe der Funktion drop_caches leeren . Beachten Sie dort unbedingt die Warnung, um zuerst die Synchronisierung auszuführen.

Greg Smith
quelle
28
Ist es möglich, das Caching innerhalb einer einzelnen Sitzung einfach zu umgehen? Wir müssen oft verschiedene Abfragen auf Leistung testen, und dieses Caching macht es sehr schwierig zu beurteilen, ob eine Methode besser als eine andere ist (außer beim Vergleich der zwischengespeicherten Leistung!)
EvilPuppetMaster
7
Es gibt keine Möglichkeit, den Cache der Datenbank zu umgehen oder zu leeren. Alles, was Sie tun können, um es zu löschen, ist den Server neu zu starten.
Greg Smith
2
Ist es denkbar, dass dies beispielsweise in der zukünftigen Entwicklung möglich gemacht wird? Oder ist dies nur etwas, was mit den aktuellen Systemen (PG und Linux) nicht möglich wäre, wenn man es versuchen würde?
Kuberchaun
9
Wenn Sie eine verwaltete PostgreSQL-Installation wie Amazon RDS verwenden, haben Sie keinen Zugriff auf das Betriebssystem, und das Leeren der Betriebssystem-Caches zu Testzwecken kann sehr schwierig sein. Daher wäre diese Funktion in PostgreSQL sehr vorteilhaft.
Samuli Pahaoja
4
Eine langsame Abfrage kann nicht reproduziert werden. Es ist ein Problem. Wie kann ich sicher sein, dass meine Abfrage nach einem Tunning ausgeführt wird? Ein Neustart des Servers ist keine Option. Ich teste die Abfrage in prod, da nur prod Parallelität, Sperren und Datensätze aufweist, die ausreichen, um das Problem zu reproduzieren
deFreitas
21

Ich habe keine Befehle zum Leeren der Caches in PostgreSQL gesehen. Was Sie sehen, sind wahrscheinlich nur normale Index- und Datencaches, die von der Festplatte gelesen und im Speicher gespeichert werden. sowohl von postgresql als auch von den Caches im Betriebssystem. Um all das loszuwerden, ist der einzige Weg, den ich kenne:

Was Sie tun sollten, ist:

  1. Fahren Sie den Datenbankserver herunter (pg_ctl, sudo service postgresql stop usw.)
  2. echo 3> / proc / sys / vm / drop_caches Dadurch werden die Datei- / Block-Caches des Betriebssystems gelöscht - sehr wichtig, obwohl ich nicht weiß, wie das auf anderen Betriebssystemen gemacht werden soll.
  3. Starten Sie den Datenbankserver
Leeeroy
quelle
1
Ich dachte, es wäre hilfreich zu beachten: Wenn sich das Datenverzeichnis von Postgres nicht auf demselben Volume befindet, auf dem '/' gemountet ist, müssen Sie möglicherweise vor / nach dem obigen Vorgang eine Bereitstellung durchführen (nicht sicher, welches wirklich). Versuchen Sie außerdem (vielleicht ein wenig Voodoo), vor und nach diesen Schritten die Synchronisierung durchzuführen.
Marqueed
17

Greg Smiths Antwort zu drop_caches war sehr hilfreich. Ich fand es notwendig, den postgresql-Dienst zu stoppen und zu starten, zusätzlich zum Löschen der Caches. Hier ist ein Shell-Skript, das den Trick macht. (Meine Umgebung ist Ubuntu 14.04 und PostgreSQL 9.3.)

#!/usr/bin/sudo bash

service postgresql stop
sync
echo 3 > /proc/sys/vm/drop_caches
service postgresql start

Ich habe mit einer Abfrage getestet, die beim ersten Mal 19 Sekunden und bei nachfolgenden Versuchen weniger als 2 Sekunden dauerte. Nach dem Ausführen dieses Skripts dauerte die Abfrage erneut 19 Sekunden.

Steve Saporta
quelle
15

Ich benutze diesen Befehl auf meiner Linux-Box:

sync; /etc/init.d/postgresql-9.0 stop; echo 1 > /proc/sys/vm/drop_caches; /etc/init.d/postgresql-9.0 start

Der Cache wird vollständig entfernt.

Mike Starov
quelle
2
Wenn die Postgresql-Version nicht 9.0 ist: sync; sudo service postgresql stop; echo 1> / proc / sys / vm / drop_caches; sudo service postgresql start
rusllonrails
@rusllonrails Das funktioniert nur, wenn der Dienst benannt ist postgresql, was möglicherweise nicht der Fall ist.
jpmc26
Ich denke, syncsollte nach dem Stoppen des Servers unmittelbar vorher erfolgen drop_caches, da Postgres während des Stoppvorgangs wieder etwas schreiben kann.
Greatvovan
8

Ja, postgresql hat sicherlich Caching. Die Größe wird durch die Einstellung shared_buffers gesteuert . Abgesehen davon gibt es, wie in der vorherigen Antwort erwähnt, den OS-Datei-Cache, der ebenfalls verwendet wird.

Wenn Sie sich ansehen möchten, was sich im Cache befindet, steht ein Contrib-Modul namens pg_buffercache zur Verfügung (in Contrib / im Quellbaum , im Contrib-RPM oder wo immer es für die Installation angemessen ist). Die Verwendung ist in der Standarddokumentation zu PostgreSQL aufgeführt.

Es gibt keine andere Möglichkeit, den Puffercache zu löschen, als den Server neu zu starten. Sie können den Betriebssystem-Cache mit dem in der anderen Antwort genannten Befehl löschen - vorausgesetzt, Ihr Betriebssystem ist Linux.

Magnus Hagander
quelle
7

Ich hatte diesen Fehler.

psql: /cygdrive/e/test_insertion.sql: 9: FEHLER: Typ des Parameters 53 (t_stat_gardien) stimmt nicht mit dem bei der Erstellung des Plans überein (t_stat_avant)

Ich suchte nach einer Spülung des aktuellen Plans und fand Folgendes:

Pläne verwerfen

Ich hatte dies zwischen meinen Einsätzen und es löst mein Problem.

Luc M.
quelle
2
Der Plan zum
Verwerfen wurde
1
Die richtige Syntax lautet DISCARD PLANS;. Und wie in der Dokumentation angegeben: "DISCARD gibt interne Ressourcen frei, die einer Datenbanksitzung zugeordnet sind ".
EAmez
6

Ja, ist es möglich , sowohl den gemeinsam genutzte Puffer Postgres - Cache zu löschen und den OS - Cache. Die folgende Lösung ist für Windows ... andere haben die Linux-Lösung bereits angegeben.

Wie bereits erwähnt, können Sie zum Löschen der freigegebenen Puffer Postgres einfach neu starten (Server muss nicht neu gestartet werden). Wenn Sie dies jedoch tun, wird der Betriebssystem-Cache nicht geleert.

Verwenden Sie die exzellente RamMap ( https://technet.microsoft.com/en-us/sysinternals/rammap ) aus der exzellenten Sysinternals Suite , um den von Postgres verwendeten Betriebssystem-Cache nach dem Beenden des Dienstes zu löschen . Sobald Sie RamMap ausgeführt haben, klicken Sie im Hauptmenü einfach auf "Leer" -> "Leere Standby-Liste".

Starten Sie Postgres neu und Sie werden sehen, dass Ihre nächste Abfrage verdammt langsam ist, da überhaupt kein Cache vorhanden ist.

Sie können die RamMap auch ausführen, ohne Postgres zu schließen, und haben wahrscheinlich die gewünschten Ergebnisse "kein Cache", da gemeinsam genutzte Puffer, wie bereits erwähnt, im Vergleich zum Betriebssystem-Cache normalerweise nur geringe Auswirkungen haben. Aber für einen zuverlässigen Test würde ich lieber Postgres wie alle stoppen, bevor ich den Betriebssystem-Cache lösche, um sicherzugehen.

Hinweis: AFAIK, ich empfehle nicht, die anderen Dinge außer "Standby-Liste" zu löschen, wenn Sie RamMap verwenden, da die anderen Daten irgendwie verwendet werden und Sie möglicherweise Probleme / lose Daten verursachen können, wenn Sie dies tun. Denken Sie daran, dass Sie nicht nur Speicher löschen, der von Postgres-Dateien verwendet wird, sondern auch alle anderen Apps und Betriebssysteme.

Grüße, Thiago L.

Thiago Linhares de Oliveira
quelle
Ich bin froh, dass es geholfen hat;)
Thiago Linhares de Oliveira
5

Das ist meine Abkürzung

echo 1 > /proc/sys/vm/drop_caches; echo 2 > /proc/sys/vm/drop_caches; echo 3 > /proc/sys/vm/drop_caches; rcpostgresql stop; rcpostgresql start;
Wutzebaer
quelle
5

Es gibt ein pg_buffercacheModul, um in den shared_buffersCache zu schauen . Und irgendwann musste ich den Cache löschen , um einige Leistungstests für den "kalten" Cache durchzuführen , also schrieb ich eine pg_dropcache- Erweiterung, die genau dies tut. Bitte probieren Sie es aus.

Ildar Musin
quelle