非常差的插入性能 MySQL / Percona Server
我在 Ubuntu 伺服器安裝中執行 Percona-Server 實例。我正在使用一個需要訪問該數據庫的應用程序,並且它的性能非常差。建立數據庫後,應用程序進入(安裝時)並創建模式。它將所有內容預設為 MyISAM,但是我已將表引擎轉換回 InnoDB。我遇到的問題是插入性能非常差。該應用程序的寫入量很大,似乎每次將每行 1 寫入磁碟,不使用任何類型的緩衝區,但是我不確定如何檢查或驗證這一點。即使從其中一個表中選擇(*)也需要 2.4 秒,並且只有 163,000 行。我有點不知所措,我還能做什麼。
伺服器有 8GB 的記憶體,在這種情況發生時 CPU 幾乎完全空閒。
我的.cnf:
[mysql] # CLIENT # port = 3306 socket = /var/run/mysqld/mysqld.sock [mysqld] # GENERAL # user = mysql default_storage_engine = InnoDB socket = /var/run/mysqld/mysqld.sock pid_file = /var/run/mysqld/mysqld.pid # MyISAM # key_buffer_size = 32M myisam_recover = FORCE,BACKUP # SAFETY # max_allowed_packet = 16M max_connect_errors = 1000000 skip_name_resolve sql_mode = STRICT_TRANS_TABLES,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_AUTO_VALUE_ON_ZERO,NO_ENGINE_SUBSTITUTION,NO_ZERO_DATE,NO_ZERO_IN_DATE,ONLY_FULL_GROUP_BY sysdate_is_now = 1 innodb = FORCE innodb_strict_mode = 1 # DATA STORAGE # datadir = /mnt/Storage/mysql/ # BINARY LOGGING # log_bin = /mnt/Storage/mysql/mysql-bin expire_logs_days = 14 sync_binlog = 1 # CACHES AND LIMITS # tmp_table_size = 32M max_heap_table_size = 32M query_cache_type = 0 query_cache_size = 0 max_connections = 500 thread_cache_size = 50 open_files_limit = 65535 table_definition_cache = 1024 table_open_cache = 2048 # INNODB # innodb_flush_method = O_DIRECT innodb_log_files_in_group = 2 innodb_log_file_size = 512M innodb_flush_log_at_trx_commit = 0 innodb_file_per_table = 1 innodb_buffer_pool_size = 6144M innodb_buffer_pool_instances = 1 innodb_read_io_threads = 64 innodb_write_io_threads = 64 innodb_io_capacity = 10000 # LOGGING # log_error = /mnt/Storage/mysql/mysql-error.log log_queries_not_using_indexes = 1 slow_query_log = 1 slow_query_log_file = /mnt/Storage/mysql/mysql-slow.log
一張插入性能較差的表的描述:
mysql> desc parts; +------------+---------------------+------+-----+---------+----------------+ | Field | Type | Null | Key | Default | Extra | +------------+---------------------+------+-----+---------+----------------+ | ID | bigint(20) unsigned | NO | PRI | NULL | auto_increment | | binaryID | int(11) unsigned | NO | MUL | 0 | | | messageID | varchar(255) | NO | | | | | number | bigint(20) unsigned | NO | MUL | 0 | | | partnumber | int(10) unsigned | NO | | 0 | | | size | bigint(20) unsigned | NO | | 0 | | | dateadded | datetime | YES | MUL | NULL | | +------------+---------------------+------+-----+---------+----------------+ 7 rows in set (0.00 sec)
觀察#1
由於你的緩衝池是 6G(6144M),innodb_log_file_size應該是 1536M(6G 的 25%)
觀察#2
您將sync_binlog設置為 1。這提供了最安全的符合 ACID 的設置。它還可以顯著減慢速度。你說
it seems as though its writing each row 1 at a time to disk
。之所以如此,是因為每個完成的 DML(INSERT、UPDATE、DELETE)和 DDL(ALTER TABLE)語句都被寫入二進制日誌。sync_binlog 的預設值為 0。讓作業系統負責將二進制日誌更改刷新到磁碟。觀察#3
您將innodb_io_capacity設置為 10000。這確實是您期望 mysql 的 10000 IOPS。嘗試降低它。
在這方面有一些事情要做
當涉及到sync_binlog
- 將其從 my.cnf 中註釋掉
- 將 sync_binlog 設置為 100 或 200 以加快二進制日誌的刷新速度
您應該確保數據磁碟具有電池支持的記憶體(具有良好的電池)
推薦
STEP 01) 在 my.cnf 中設置這些選項
[mysqld] innodb_fast_shutdown = 0 innodb_log_file_size = 1536M sync_binlog = ( you choose 0 or 100 )
步驟 02)刪除 innodb_io_capacity。讓它設置為預設值。
步驟 03) 在 mysql 中執行此命令
mysql> SET GLOBAL innodb_fast_shutdown = 0;
STEP 04) 應用設置
cd /mnt/Storage/mysql service mysql stop mv ib_logfile0 ib_logfile0.bak mv ib_logfile2 ib_logfile1.bak service mysql start
這應該加快速度