MySQL-InnoDB-Schreibvorgänge sind extrem langsam


8

Ich habe ernsthafte Leistungsprobleme mit MySQL und der InnoDB-Engine. Selbst die einfachste Tabelle macht das Schreiben (Erstellen der Tabelle, Einfügen, Aktualisieren und Löschen) schrecklich langsam, wie Sie im folgenden Ausschnitt sehen können.

mysql> CREATE TABLE `test` (`id` int(11) not null auto_increment,
   -> PRIMARY KEY(`id`)) ENGINE=InnoDB;
Query OK, 0 rows affected (4.61 sec)

mysql> insert into test values ();
Query OK, 1 row affected (1.92 sec)

mysql> insert into test values ();
Query OK, 1 row affected (0.88 sec)

mysql> insert into test values ();
Query OK, 1 row affected (1.10 sec)

mysql> insert into test values ();
Query OK, 1 row affected (6.27 sec)

mysql> select * from test;
+----+
| id |
+----+
|  1 |
|  2 |
|  3 |
|  4 |
+----+
4 rows in set (0.00 sec)

mysql> delete from test where id = 2;
Query OK, 1 row affected (0.28 sec)

mysql> delete from test where id = 3;
Query OK, 1 row affected (6.37 sec)

Ich habe mir htop angesehen und die langen Wartezeiten sind nicht auf eine abnormale CPU-Auslastung zurückzuführen. Es ist fast Null und die Speichernutzung ist ebenfalls normal. Wenn ich dieselbe Tabelle mit der MyISAM-Engine erstelle, funktioniert dies normal. Meine my.cnf-Datei enthält Folgendes (wenn ich mich recht erinnere, habe ich nichts an der Standard-Debian-Konfiguration geändert):

[client]
port        = 3306
socket      = /var/run/mysqld/mysqld.sock
[mysqld_safe]
socket      = /var/run/mysqld/mysqld.sock
nice        = 0

[mysqld]
user        = mysql
pid-file    = /var/run/mysqld/mysqld.pid
socket      = /var/run/mysqld/mysqld.sock
port        = 3306
basedir     = /usr
datadir     = /var/lib/mysql
tmpdir      = /tmp
language    = /usr/share/mysql/english
skip-external-locking
bind-address        = 127.0.0.1
key_buffer      = 40M
max_allowed_packet  = 16M
thread_stack        = 128K
thread_cache_size       = 8
myisam-recover         = BACKUP
max_connections        = 100
table_cache            = 64
thread_concurrency     = 10
query_cache_limit   = 1M
query_cache_size        = 40M
log_slow_queries    = /var/log/mysql/mysql-slow.log
long_query_time = 2
log-queries-not-using-indexes
expire_logs_days    = 10
max_binlog_size         = 100M

[mysqldump]
quick
quote-names
max_allowed_packet  = 16M

[isamchk]
key_buffer      = 16M
!includedir /etc/mysql/conf.d/

Ich habe auch versucht, den Server neu zu starten, aber es löst nichts.

Das Protokoll für langsame Abfragen enthält keine zusätzlichen Informationen.


Normalerweise sind die Linux-Standard-MySQL-Setups nicht für eine optimale Innodb-Nutzung konfiguriert. Google 'MySQL Linux einstellen, um Innodb zu verwenden'.

Ist dies eine lokale virtuelle Maschine auf Ihrer Workstation?
Mannoj

Es ist eine VM, aber nicht lokal. Es ist ein kostenpflichtiges Hosting.
Ximo Puig Bruguera

können Sie einige iostatInformationen während der Einfügung geben, das Ergebnis für SHOW VARIABLES LIKE '%version%'undSHOW VARIABLES LIKE '%innodb%';
altmannmarcelo

Antworten:


6
  • innodb_flush_log_at_trx_commit = 2für bessere Geschwindigkeit ( =1für bessere Sicherheit)

  • sync_binlog = 0 Wenn Sie das Binlog nicht verwenden.

  • "Batch" INSERTs - viele Zeilen in einer einzigen INSERTAnweisung. (Wenn Sie viele haben, machen Sie jeweils 100.) Ist LOAD DATAauch hervorragend zum Laden geeignet.

  • innodb_buffer_pool_size = 70% des verfügbaren Arbeitsspeichers.

  • auto_commit = 1oder verwenden BEGIN ... COMMIT

  • thread_stack = 256K Ich bin überrascht, dass es mit Ihrem kleinen Wert nicht abgestürzt ist.

Trotzdem sind die Zeiten (1s-6s) völlig unvernünftig. Selbst wenn alles "falsch" eingestellt ist, sollten 0,1s für eine einfache INSERTerwartet werden.

Läuft das in einer "Wolke"? Ist noch etwas los?



0

Stellen Sie bitte sicher, dass Sie innodb_buffer_pool_size80% des Speichers Ihrer VM haben. Nehmen Sie weitere Änderungen für InnoDB vor, die für Ihre Anwendung am besten geeignet sind. Nachfolgend einige Empfehlungen. Versuchen buffer_poolSie zuerst, mich wissen zu lassen, wie die Beilagen für Sie aussehen.

default-storage-engine         
innodb_file_per_table          
innodb_additional_mem_pool_size    
innodb_buffer_pool_size            
innodb_thread_concurrency          
innodb_flush_log_at_trx_commit     
innodb_log_buffer_size             
innodb_log_file_size               
innodb_log_files_in_group          
innodb_max_dirty_pages_pct         
innodb_lock_wait_timeout           

Tatsächlich kann innodb_file_per_table es verlangsamen, wenn Sie viele Tabellen haben. Dies liegt daran, dass mysql sync () aufrufen und warten muss, bis der Kernel für jede Datendatei zurückkehrt, anstatt sie nur einmal aufrufen zu müssen.
Sarel Botha

0

Wenn Ihre Datenbank bereits langsam ist, kann das Ausführen von Batch-Einfügungen Ihre Leistung weiter verringern. Insbesondere in InnoDB, wo jeder Schreibvorgang in Transaktionsprotokollen aufgezeichnet wird.

Schlagen Sie vor, dass Sie zuerst Ihr System optimieren und / oder die Hardware aktualisieren, bevor Sie die Vorteile von Batch-Einfügungen in InnoDB nutzen.


1
Im Gegenteil, Batch INSERTs profitieren auf zwei Arten: (a) weniger Overhead im Netzwerk / Parsing / usw. und (b) weniger COMMITs.
Rick James

@ RickJames das stimmt im Allgemeinen. Zum Debuggen langsamer Datenbankinstanzen hilft der vorgeschlagene Ansatz (Optimieren der Datenbankeinstellungen und / oder Hardware-Aktualisierung).
Vinay Vemula
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.