Mysql
 sql >> Datenbank >  >> RDS >> Mysql

InnoDB-Indizes vor und nach dem Importieren

Ich habe bei einem früheren Job ein wenig mit diesem Konzept experimentiert, wo wir eine schnelle Methode zum Kopieren von Schemas zwischen MySQL-Servern brauchten.

Beim Einfügen in Tabellen mit Sekundärindizes entsteht tatsächlich ein Performance-Overhead. Einfügungen müssen den gruppierten Index (auch bekannt als die Tabelle) aktualisieren und auch sekundäre Indizes aktualisieren. Je mehr Indizes eine Tabelle hat, desto mehr Overhead verursacht sie für Einfügungen.

InnoDB hat eine Funktion namens Änderungspuffer was ein wenig hilft, indem Indexaktualisierungen verschoben werden, aber sie müssen schließlich zusammengeführt werden.

Einfügungen in eine Tabelle ohne sekundäre Indizes sind schneller, daher ist es verlockend zu versuchen, die Indexerstellung zu verschieben, bis Ihre Daten geladen sind, wie Sie es beschreiben.

Percona Server, ein Zweig von MySQL, experimentierte mit einem mysqldump --optimize-keys Möglichkeit. Wenn Sie diese Option verwenden, ändert sie die Ausgabe von mysqldump so, dass sie CREATE TABLE ohne Indizes enthält, dann INSERT alle Daten und dann ALTER TABLE, um die Indizes hinzuzufügen, nachdem die Daten geladen wurden. Siehe https://www.percona.com/doc/ percona-server/LATEST/management/innodb_expanded_fast_index_creation.html

Aber meiner Erfahrung nach war die Nettoleistungsverbesserung gering. Es dauert immer noch eine Weile, viele Zeilen einzufügen, selbst bei Tabellen ohne Indizes. Dann muss die Wiederherstellung eine ALTER TABLE ausführen, um die Indizes zu erstellen. Dies dauert bei einer großen Tabelle eine Weile. Wenn Sie die Zeit für INSERTs plus die zusätzliche Zeit zum Erstellen von Indizes zählen, ist es nur ein paar (niedrige einstellige) Prozent schneller als das Einfügen auf herkömmliche Weise in eine Tabelle mit Indizes.

Ein weiterer Vorteil dieser nachträglichen Indexerstellung besteht darin, dass die Indizes kompakter gespeichert werden. Wenn Sie also Speicherplatz sparen müssen, ist dies ein besserer Grund, diese Technik zu verwenden.

Ich fand es viel leistungsstärker, die Wiederherstellung durch paralleles Laden mehrerer Tabellen durchzuführen .

  • Das neue MySQL 8.0-Tool mysqlpump unterstützt Multithread-Dump.
  • Das Open-Source-Tool mydumper unterstützt Multithread-Dump und hat auch ein Multithread-Wiederherstellungstool namens myloader . Der schlimmste Nachteil von mydumper/myloader ist, dass die Dokumentation praktisch nicht existiert, also müssen Sie ein unerschrockener Power-User sein, um herauszufinden, wie man es ausführt.

Eine andere Strategie ist die Verwendung von mysqldump --tab um CSV-Dateien anstelle von SQL-Skripten auszugeben. Das Massenladen von CSV-Dateien ist viel schneller als das Ausführen von SQL-Skripts zum Wiederherstellen der Daten. Nun, es gibt eine SQL-Datei für die Tabellendefinition und eine CSV-Datei für die zu importierenden Daten aus. Es erstellt separate Dateien für jede Tabelle. Sie müssen die Tabellen manuell neu erstellen, indem Sie alle SQL-Dateien laden (das geht schnell) und dann mysqlimport um die CSV-Dateien zu laden. Das Tool mysqlimport hat sogar einen --use-threads Option zur parallelen Ausführung.

Testen Sie sorgfältig mit einer unterschiedlichen Anzahl paralleler Threads. Meine Erfahrung ist, dass 4 Threads am besten sind. Bei größerer Parallelität wird InnoDB zum Flaschenhals. Abhängig von der MySQL-Version und der Leistungsfähigkeit Ihrer Serverhardware können Ihre Erfahrungen jedoch unterschiedlich sein.

Die allerschnellste Wiederherstellungsmethode ist die Verwendung eines physischen Backup-Tools, die beliebteste ist Percona XtraBackup . Dies ermöglicht schnelle Backups und noch schnellere Wiederherstellungen. Die gesicherten Dateien können buchstäblich kopiert und als Live-Tablespace-Dateien verwendet werden. Der Nachteil ist, dass Sie Ihren MySQL-Server herunterfahren müssen, um die Wiederherstellung durchzuführen.