Warum produziert MySQL so viele temporäre MYD-Dateien?

9

Auf einem Debian Linux-Server, auf dem viele PHP / MySQL-Websites (Fotogalerien) gehostet werden, habe ich manchmal "viele" Dateien wie /tmp/#sql_6405_58.MYD.

Zum Beispiel heute:

[2012-12-15 15:18:11] /tmp/#sql_6405_6.MYD : 88MB
[2012-12-15 15:18:11] /tmp/#sql_6405_3.MYD : 22MB
[2012-12-15 15:18:11] /tmp/#sql_6405_4.MYD : 138MB
[2012-12-15 15:18:11] /tmp/#sql_6405_10.MYD : 88MB
...
[2012-12-15 15:18:11] /tmp/#sql_6405_9.MYD : 15MB
[2012-12-15 15:18:11] /tmp/#sql_6405_65.MYD : 49MB
[2012-12-15 15:18:11] /tmp/#sql_6405_44.MYD : 69MB

(59 Dateien gleichzeitig, für mehr als 6 GB ... ja, ich überwache große Dateien in / tmp)

Leider /tmpist auf der gleichen Partition als /und es bricht vorübergehend den Webserver, weil /es wohl voll ist. Dann verschwinden die Dateien und der Server ist wieder normal.

Alle Dateinamen folgen dem #sql_6405_*.MYDMuster. Ich würde gerne verstehen, welche MySQL-Operation so viele temporäre Dateien impliziert. Ich habe ungefähr 2000 Datenbanken auf diesem Server. Ist es möglich zu wissen, um welche Datenbank es sich handelt?

RolandoMySQLDBA
quelle
1
Ich vermute, es handelt sich um temporäre Daten für große Vorgänge, die verwendet werden filesort, und 6405 ist die PID von MySQL, um temporäre Dateien von verschiedenen Serverinstanzen getrennt zu halten.
Soll ich einen Administrator bitten, meine Frage zu verschieben?

Antworten:

14

Es gibt einige Optionen, die dazu führen können, dass temporäre Tabellen als MyISAM-Tabellen angezeigt werden oder so konfiguriert werden können, dass sie verzögert werden. Beachten Sie, dass es für festplattenbasierte temporäre Tabellen keine .frmDateien gibt, sondern nur Dateien .MYDund .MYIDateien (natürlich wird die .MYI-Datei nie verwendet, da es unmöglich ist, eine interne temporäre Tabelle zu indizieren).

Hier sind die Optionen:

Sie sollten auch die MySQL-Dokumentation zur Verwendung interner temporärer Tabellen berücksichtigen

Die Situationen, in denen speicherinterne temporäre Tabellen erstellt werden, sind:

  • Wenn es eine ORDER BY-Klausel und eine andere GROUP BY-Klausel gibt oder wenn ORDER BY oder GROUP BY Spalten aus anderen Tabellen als der ersten Tabelle in der Join-Warteschlange enthält, wird eine temporäre Tabelle erstellt.
  • DISTINCT in Kombination mit ORDER BY erfordert möglicherweise eine temporäre Tabelle.
  • Wenn Sie die Option SQL_SMALL_RESULT verwenden, verwendet MySQL eine temporäre In-Memory-Tabelle, es sei denn, die Abfrage enthält auch Elemente (später beschrieben), die Speicher auf der Festplatte erfordern.

Wenn eine speicherinterne temporäre Tabelle das Minimum von (tmp_table_size oder max_heap_table_size) überschreitet, führt mysqld Folgendes aus:

  • Hält die Abfrage an
  • Kopiert den Inhalt der In-Memory-Tabelle in eine MyISAM-temporäre Tabelle
  • Verwirft die In-Memory-Tabelle
  • Setzt die Abfrage fort und sendet die temporären Daten an die temporäre MyISAM-Tabelle

Die Situationen, in denen speicherinterne temporäre Tabellen zugunsten der Festplatte umgangen werden, sind:

  • Vorhandensein einer BLOB- oder TEXT-Spalte in der Tabelle
  • Vorhandensein einer Spalte in einer GROUP BY- oder DISTINCT-Klausel, die größer als 512 Byte ist
  • Vorhandensein einer Spalte mit mehr als 512 Byte in der SELECT-Liste, wenn UNION oder UNION ALL verwendet wird

Es ist eine gewisse Sorgfalt erforderlich, um die Erstellung temporärer Tabellen auf der Festplatte zu reduzieren

  • Setzen Sie join_buffer_size größer
  • Setze sort_buffer_size größer
  • Setzen Sie tmp_table_size und max_heap_table_size größer
  • Optimieren von Abfragen, um temporäre Tabellen zu minimieren oder sogar zu verhindern
  • Erstellen von Indizes zum Erstellen einer vorsortierten Ansicht von Daten aus einzelnen Tabellen
  • Installieren von zusätzlichem RAM für große temporäre In-Memory-Tabellen

Wenn nach einer solchen Due Diligence noch temporäre Tabellen auf der Festplatte erstellt werden, ist hier ein verzweifelter Schritt: Zuordnen der festplattenbasierten temporären Tabellenerstellung zum Speicher.

Hier ist eine schnelle und schmutzige Möglichkeit, eine 16-GB-RAM-Disk mit tmpdir einzurichten

SCHRITT01) RAM-Disk-Ordner erstellen

mkdir /var/mysql_tmpfs

SCHRITT02) Fügen Sie dies hinzu my.cnf

[mysqld]
tmpdir=/var/mysql_tmpfs

SCHRITT03) Fügen Sie dies zu / etc / fstab hinzu

echo "none /var/mysql_tmpfs tmpfs defaults,size=16g 1 2" >> /etc/fstab

SCHRITT 04) Laden Sie / etc / fstab neu

mount -a

SCHRITT 05) service mysql restart

Danach werden alle temporären Tabellen, die zu MyISAM werden, auf die RAM-Disk geschrieben. Dies sollte die Erstellung einer festplattenbasierten temporären Tabelle beschleunigen.

Versuche es !!!

RolandoMySQLDBA
quelle
1

Hierbei handelt es sich um Abfragen, die auf die Festplatte übertragen werden, da die Ergebnisse für den Speicher zu groß sind.

Wenn die Abfrage abgeschlossen ist, wird der Platz gelöscht.

Es gibt keine Möglichkeit, diese temporären Dateien definitiv mit Abfragen abzugleichen, aber Sie können Hinweise erhalten, um eine gute Vermutung aus SHOW FULL PROCESSLIST zu ziehen. oder SHOW INNODB STATUS; oder indem Sie in Ihrem Fehlerprotokoll nachsehen, ob die Abfragen fehlschlagen.

Valerie Parham-Thompson
quelle
1

Wann immer wir alter-Anweisungen für die Tabelle verwenden, werden die temporären Dateien # sql_6405_3.MYD erstellt. Sobald dies erledigt ist, wird die Ausgabe ausgelöst und verschwindet.

Durch Ändern von Tabellen kann MySQL ganze Daten in temporäre Dateien # sql.xxx.MYD kopieren und Änderungen an erstellten temporären Dateien vornehmen. Anschließend werden die ursprünglichen Datendateien tablename.MYD gelöscht und die temporären Dateien in Tabellennamen umbenannt.

Auch für einige Sortierabfragen werden temporäre Dateien erstellt.

Wie ich ausfindig gemacht habe. Das passiert.

Vinay
quelle
0

Ich denke, Sie finden die fraglichen Abfragen möglicherweise im langsamen Abfrageprotokoll, da Abfragen, die große temporäre Tabellen erstellen, normalerweise lange ausgeführt werden. Dies hat mir heute auf einem Server geholfen, auf dem ich festgestellt habe, dass die /tmpPartition aufgrund einer ähnlichen Funktion voll ist große MySQL-temporäre Datei, es war eine 4G-Datei, ich fand die Abfrage im langsamen Abfrageprotokoll und meldete die Abfrage an Entwickler, und sie fanden die Beschädigung in der Abfrage und sie werden sie beheben für eine lange Zeit und schrieb eine 4G-temporäre Datei und füllte /tmpPartition aus.

Und es gibt noch eine andere Möglichkeit, herauszufinden, was diese große temporäre Datei verursacht hat. Sie ist binär, sodass Sie sie nicht direkt lesen können. Ich habe jedoch festgestellt, dass Sie den darin enthaltenen Text mithilfe des Linux-Befehls string wie folgt erfassen können.

strings name-of-mysql-temp-file

Ich habe anhand der Textwörter sichergestellt, welche MySQL-Abfrage ausgeführt und erstellt wurde.

linuxman1
quelle