高性能mysql
2017年7月11日
第8章 優化服務器設置
如果不知道配置路徑
$ which myslqd
/usr/sbin/mysqld –verbose –help | grep -A 1 ‘Default options’
8.3 創建mysql 配置文件
不要把Socket文件和PID文件放到Mysql編譯默認的位置,在不同的Mysql版本里這可能導致一些錯誤
- 設置緩衝池
8.4配置內存使用
- 重要緩存分配
- 大日誌提升性能 innodb_max_dirty_pages_pct
- 查看MYISAM索引佔用的實際空間
select SUM(INDEX_LENGTH) FROM INFORMATION_SCHEMA.TABLES where engine=’MYISAM’;
unix
du -sch ‘find /path/to/mysql/data/directory/ -name “*.MYI”’
- CACHE INDEX 命令將表映射到對應緩衝區
mysql> CACHE INDEX t1,t2 key_buffer_1;
mysql > LOAD INDEX INTO CACHE t1,t2; - 鍵緩衝公式
- 獲取狀態值變化量
$mysqladmin extended-status -r -i 10|grep key_reads - fincore 工具可以看到那些塊在緩存中
- InodeDB爲每個.ibd文件使用單個、全局的文件描述符,所以最好設置足夠大
- CACHE INDEX 命令將表映射到對應緩衝區
8.5 配置MySql 的IO/行爲
- INnoDB事務日誌
innodb_flush_log_at_trx_commit 變量控制日誌緩衝刷新的頻繁程度
0
把日誌緩衝寫到日誌文件,並且每秒種刷新一次,但是事物提交不做任何事。
1
把日誌緩衝寫到日誌文件,每次事物持久化存儲。默認(安全)
2
把日誌緩衝寫到日誌文件,但是並不刷新。如果mysql進程”掛了”2不會丟失日誌,如果整個服務器”掛了”或者斷電丟失一些事務。 - MyISAM 的I/O配置
mysql> show variables like ‘myisam_recover_options’; #檢查是否損壞
8.6配置Mysql併發
innodb_thread_concurrency = 32 # 限制併發 併發值=CPU數量*磁盤量*2
concurrent_insert
0
MyISAM 不允許併發插入,所有插入都會對錶加互斥鎖
1
默認值,只要表沒有空洞,允許併發操作
8.7 基於工作負載配置
innotop 監控服務器 pt-query-digest 創建查詢報告 創建 processlist快照 腳本查看第三章
注意事項
- 服務器不能再內存臨時表中存儲BLOB值,
- 使用 SUBSTRING() 函數把值把VARCHAR
- 變長列 InnoDB 存儲一個768字節的前綴在行內。
- 優化排序(Filesorts)
max_length_for_sort_data 操過這個使用two-pass,否則使用single-pass
tmp_table_size
max_heap_table_size = 64M # 使用Memory 引擎的臨時表能使用多大的內存,如果隱式臨時表超過這兩個值,則轉換爲MyISAM
8.9 安全和穩定的設置
- expire_logs_days = 7 # 自動清理二進制日誌
- max_allowed_packet = 16M # 這個設置防止服務器發送太大的包
- max_connect_errors = 10000 # 有效禁止主機黑名單
- skip_name_resolve # 禁用了另一個網絡相關和鑑權認證相關的陷阱:DNS查找
驗證主機名,爲了導致超時,基於主機名的授權改爲用ip地址、通配符。 - sql_mode 這個設定可以接受多種多樣的值來確定改變服務器的行爲。
- sysdate_is_now
防止備庫問題
- read_only # 只接受來自主庫傳輸過來的變更,不接受從應用來的變更。建議將備庫設置爲read_only
- skip_slave_start # 這個選項阻止mysql試圖自動啓動複製
- slave_net_timeout # 設置備庫和主庫連接失敗並且需要重新連接的等待時間。
- relay_log 在好的硬件下建議打開,可以從崩潰中恢復
- overwrite_relay_log_info 可以讓InoDB在事務日誌重存儲複製的位置。
8.10 高級InnoDB 設置
- innodb_autoinc_lock_mode 自增主鍵值,高併發情況下,自增主鍵值可能是個瓶頸。
- innodb_buffer_pool_instances = 8 # 把緩衝池切分成多段,可能是在高負載的多核機器上提升mysql可擴展性
- innodb_io_capacity = 500 # 處理IO的能力,刷新髒頁 PCI-E SSD 可以設置爲上萬
- innodb_read_io_threads = 16 # 控制有多少後臺線程可以被I/O操作使用
innodb_write_io_threads = 16 # 控制有多少後臺線程可以被I/O操作使用
- innodb_read_io_threads = 16 # 控制有多少後臺線程可以被I/O操作使用
- innodb_strict_mode 將某些條件下把警告改成拋錯
- innodb_old_blocks_time = 1000 # 指定一個頁面從LRU鏈表的“年輕” 部分轉移到“年老” 部分之間必須經過的毫秒數 1000毫秒=1秒
8.11 總結
使用InnoDB,兩個最重要的選項
- innodb_buffer_pool_size
- innodb_log_file_size
在線工具
建議:不要”調優“ 服務器,不要信任網上不明身份的人的意見,不要去不斷的刷show status
配置表
# my.cnf
[client]
port = 3306
socket = /log/mysql/mysql.sock
[mysqld_multi]
mysqld = /app/mysql/bin/mysqld_safe
mysqladmin = /app/mysql/bin/mysqladmin
log = /log/mysql/multi.log
[mysqld1]
port = 3307
socket = /log/mysql_1/mysql.sock
pid-file = /log/mysql_1/mysqld.pid
log-error = /log/mysql_1/error.log
datadir = /data/mysql_1
tmpdir = /data/mysql_1
slow_query_log_file = /log/mysql_1/slow.log
relay-log = mysqld-relay-bin
long_query_time = 1
slow_query_log = 1
sql_mode = "NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
transaction_isolation = REPEATABLE-READ
old_passwords = 0
back_log = 1024 # 要求MySQL能有的連接數量
open_files_limit = 65535
explicit_defaults_for_timestamp = 1
default-storage-engine=InnoDB
performance_schema = 0
max_connections = 16384
table_open_cache = 8192 # 表緩存,爲每個線程、每個表使用
thread_concurrency = 32
max_connect_errors = 10000 # 有效禁止主機黑名單
interactive_timeout = 512
wait_timeout = 256
max_allowed_packet = 16M
binlog_cache_size = 1M
max_heap_table_size = 64M # 使用Memory 引擎的臨時表能使用多大的內存
sort_buffer_size = 2M
join_buffer_size = 2M
# 8 + (max_connections / 100)
thread_cache_size = 1024
query_cache_size = 0
query_cache_type = 0
#query_cache_limit = 16M
#default_table_type = INNODB
skip-external-locking
skip-name-resolve
server-id = 525
#*** master ***
#log-bin= bin-log
#binlog-format = ROW
#binlog_rows_query_log_events = 1
#expire_logs_days = 7
replicate-wild-ignore-table = mysql.%
replicate-wild-ignore-table = test.%
replicate-wild-ignore-table = information_schema.%
replicate-wild-ignore-table = performance_schema.%
#*** MyISAM Specific options ***
key_buffer_size = 32M
read_buffer_size = 2M
read_rnd_buffer_size = 16M
innodb_buffer_pool_instances = 8
innodb_old_blocks_time = 1000
innodb_buffer_pool_size = 16G
innodb_log_group_home_dir = /data/mysql_1
innodb_data_home_dir = /data/mysql_1
innodb_data_file_path = ibdata1:1G:autoextend
innodb_autoextend_increment = 64
innodb_read_io_threads = 16 # 控制有多少後臺線程可以被I/O操作使用
innodb_write_io_threads = 16 # 控制有多少後臺線程可以被I/O操作使用
innodb_thread_concurrency = 32
innodb_flush_log_at_trx_commit = 2 # 把日誌緩衝寫到日誌文件,但是並不刷新。如果mysql進程"掛了"2不會丟失日誌,如果整個服務器"掛了"或者斷電丟失一些事務。
innodb_log_buffer_size = 128M
innodb_log_files_in_group = 2
innodb_log_file_size = 1G
innodb_open_files = 16384
innodb_file_per_table = 1 # 每張表使用一個文件 .ibd
innodb_purge_threads = 1
innodb_stats_persistent = 0
innodb_io_capacity = 500
innodb_max_dirty_pages_pct = 80
innodb_adaptive_flushing = 0
innodb_file_format = barracuda
innodb_adaptive_hash_index = 0
#zfs
#innodb_use_native_aio = 0
#innodb_doublewrite = 0
#innodb_flush_method = O_DSYNC
innodb_flush_method = O_DIRECT # 非windows 用fsync()
innodb_use_native_aio = 1
innodb_doublewrite = 1 # 雙寫緩衝
#innodb_sync_spin_loops = 100
#innodb_spin_wait_delay = 96
#innodb_checksum_algorithm = NONE
### slave ###
#skip_slave_start # 這個選項阻止mysql試圖自動啓動複製
slave_compressed_protocol = 1
slave_parallel_workers = 0
master-info-repository = TABLE
relay-log-info-repository = TABLE
slave_type_conversions = ALL_NON_LOSSY
[mysqld2]
port = 3306
socket = /log/mysql/mysql.sock
pid-file = /log/mysql/mysqld.pid
log-error = /log/mysql/error.log
datadir = /data/mysql
tmpdir = /data/mysql
slow_query_log_file = /log/mysql/slow.log
relay-log = mysqld-relay-bin
long_query_time = 1
slow_query_log = 1
sql_mode = "NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION"
transaction_isolation = REPEATABLE-READ
old_passwords = 0
back_log = 1024
open_files_limit = 65535 # 打開文件太多(too many open files)
explicit_defaults_for_timestamp = 1
default-storage-engine=InnoDB
performance_schema = 0
max_connections = 16384 #最大連接數 ”MySQL: ERROR 1040: Too many connections”的情況
table_open_cache = 8192
thread_concurrency = 32
max_connect_errors = 10000 # 每個主機在連接請求異常中斷的最大次數,當超過該次數,則禁止host的連接請求,直到服務器重啓或flush hosts命令清空該host的相關信息
interactive_timeout = 512
wait_timeout = 256
max_allowed_packet = 16M # 這個設置防止服務器發送太大的包
binlog_cache_size = 1M
max_heap_table_size = 64M # 可創建的內存表大小
sort_buffer_size = 2M
join_buffer_size = 2M
# 8 + (max_connections / 100)
thread_cache_size = 1024
query_cache_size = 0
query_cache_type = 0
#query_cache_limit = 16M
#default_table_type = INNODB
skip-external-locking
skip-name-resolve
server-id = 525
#*** master ***
#log-bin= bin-log
#binlog-format = ROW
#binlog_rows_query_log_events = 1
#expire_logs_days = 7 # 自動清理二進制日誌
replicate-wild-ignore-table = mysql.%
replicate-wild-ignore-table = test.%
replicate-wild-ignore-table = information_schema.%
replicate-wild-ignore-table = performance_schema.%
#*** MyISAM Specific options ***
key_buffer_size = 32M # GROUP BY 語句可能會使用MyISAM做臨時表
read_buffer_size = 2M
read_rnd_buffer_size = 16M
innodb_buffer_pool_instances = 8 # 把緩衝池切分成多段,可能是在高負載的多核機器上提升mysql可擴展性
innodb_old_blocks_time = 1000 # 指定一個頁面從LRU鏈表的“年輕” 部分轉移到“年老” 部分之間必須經過的毫秒數
innodb_buffer_pool_size = 8G
innodb_log_group_home_dir = /data/mysql
innodb_data_home_dir = /data/mysql #InnoDB 表空間 不能簡單的刪除或者改變大小
innodb_data_file_path = ibdata1:1G:autoextend
innodb_autoextend_increment = 64
innodb_read_io_threads = 16
innodb_write_io_threads = 16
innodb_thread_concurrency = 32 # 限制併發 併發值=CPU數量*磁盤量*2 實際中小一點更好
innodb_flush_log_at_trx_commit = 2
innodb_log_buffer_size = 128M
innodb_log_files_in_group = 2
innodb_log_file_size = 1G
innodb_open_files = 16384
innodb_file_per_table = 1
innodb_purge_threads = 1
innodb_stats_persistent = 0
innodb_io_capacity = 500 # 處理IO的能力,刷新髒頁 PCI-E SSD 可以設置爲上萬
innodb_max_dirty_pages_pct = 80
innodb_adaptive_flushing = 0
innodb_file_format = barracuda
innodb_adaptive_hash_index = 0
#zfs
#innodb_use_native_aio = 0
#innodb_doublewrite = 0
#innodb_flush_method = O_DSYNC
innodb_flush_method = O_DIRECT # 取決系統,通常需要帶寫換成的RAID卡 widows下默認使用async_unbuffered
innodb_use_native_aio = 1
innodb_doublewrite = 1
#innodb_sync_spin_loops = 100
#innodb_spin_wait_delay = 96
#innodb_checksum_algorithm = NONE
[mysqldump]
quick
max_allowed_packet = 16M
[mysql]
no-auto-rehash
[mysqlhotcopy]
interactive-timeout
[mysqld_safe]
open-files-limit = 65535
#pid-file = logs/mysqld.pid