簡介:mysql
數據庫的東西,每每一個參數就牽涉N多知識點。因此簡單的說一下。你們都知道innodb是支持事務的存儲引擎。事務的四個特性ACID即原子性(atomicity),一致性(consistency),隔離性(isolation),持久性(durability)。其中原子性,一致性,持久性經過redo log 和 undo來實現。redo log稱爲重作日誌,用來保證事務的原子性和持久性。undo log用來保證事務的一致性。 當事務提交時,必須先將該事務的全部日誌寫入到重作日誌文件(redo log)進行持久化(固然先寫到日誌緩衝區,而不是直接寫文件,關於何時刷新到磁盤文件,是一個比較複雜的問題,同窗們自行查閱資料),待事務提交操做纔算完成。innodb的redo log是順序I/O,因此設置合適的值可以大大提升數據庫性能。那麼是否是設置的越大越好呢?sql
設置的過小:當一個日誌文件寫滿後,innodb會自動切換到另一個日誌文件,並且會觸發數據庫的檢查點(Checkpoint),這會致使innodb緩存髒頁的小批量刷新,會明顯下降innodb的性能。數據庫
設置的太大:設置很大之後減小了checkpoint,而且因爲redo log是順序I/O,大大提升了I/O性能。可是若是數據庫意外出現了問題,好比意外宕機,那麼須要重放日誌而且恢復已經提交的事務,若是日誌很大,那麼將會致使恢復時間很長。甚至到咱們不能接受的程度。緩存
那麼咱們如何估算log file該設置爲多大?一般咱們能夠經過觀察show status中innodb_os_log_written狀態變量來查看innodb對日誌文件寫出了多少數據。一個好用的經驗是,查看10-100秒間隔的數字,而後記錄峯值。能夠用這個判斷日誌緩衝是否設置的正好。例如,若看到峯值是每秒寫100kb數據到日誌,那麼1MB的日誌緩衝已經足夠了。也可使用這個衡量標準來決定日誌文件設置多大會比較好。若是峯值是100KB/s,那麼256M的日誌文件足夠存儲至少2560秒的日誌記錄。通常來講,日誌文件的所有大小,應該足夠容納服務器一個小時的活動內容。服務器
下面看實際的測試(因爲是虛擬機,因此使用sysbench模擬據量寫入,生產環境選擇數據庫最繁忙的時候測試):socket
[root@yayun-mysql-server ~]# sysbench --test=oltp --oltp-table-size=100000 --oltp-read-only=off --init-rng=on --num-threads=16 --max-requests=0 --oltp-dist-type=uniform --max-time=180 --mysql-user=root --mysql-socket=/tmp/mysqld.sock --mysql-password=123456 --db-driver=mysql --mysql-table-engine=innodb --oltp-test-mode=complex prepare
1.首先計算innodb每分鐘產生的日誌量:性能
(root@yayun-mysql-server) [(none)]>pager grep sequence PAGER set to 'grep sequence' (root@yayun-mysql-server) [(none)]>show engine innodb status\G select sleep(60); show engine innodb status\G Log sequence number 6377275259 1 row in set (0.00 sec) 1 row in set (1 min 0.00 sec) Log sequence number 6403945555 1 row in set (0.00 sec) (root@yayun-mysql-server) [(none)]>nopager PAGER set to stdout (root@yayun-mysql-server) [(none)]>select (6403945555 - 6377275259) / 1024 / 1024 as MB_per_min; +-------------+ | MB_per_min | +-------------+ | 25.43477631 | +-------------+ 1 row in set (0.02 sec) (root@yayun-mysql-server) [(none)]>
注意Log sequence number,這是寫入事務日誌的總字節數。因此,如今你能夠看到每分鐘有多少MB日誌寫入(這裏的技術適用於全部版本的MySQL,在5.0及更高版本,你能夠從SHOW GLOBAL STATUS的輸出看Innodb_os_log_written的值) 。測試
經過計算後獲得每分鐘有25M的日誌寫入。atom
根據經驗法則。一般咱們設置redo log size足夠大,可以容納1個小時的日誌寫入量。spa
1小時日誌寫入量=25M * 60=1500M,大約等於1.5G。因爲默認有兩個日誌重作日誌文件ib_logfile0和ib_logfile1。在日誌組中的每一個重作日誌文件的大小一致,並以循環的方式寫入。innodb存儲引擎先寫重作日誌文件0,當達到文件的最後時,會切換到重作日誌1,並checkpoint。以此循環。
因此咱們能夠大約設置innodb_log_file_size=800M。注意:在innodb1.2.x版本以前,重作日誌文件總的大小不得大於等於4G,而1.2.x版本將該限制擴大到了521G。
innodb_log_file_size = 800M
[root@yayun-mysql-server mysql]# du -sh ib_logfile* 801M ib_logfile0 801M ib_logfile1 [root@yayun-mysql-server mysql]#
對於innodb 1.2.x版本以前若是設置大於4G則報錯
[root@yayun-mysql-server mysql]# tail -n 10 yayun-mysql-server.err 140511 1:01:15 InnoDB: Completed initialization of buffer pool 140511 1:01:15 InnoDB: Error: combined size of log files must be < 4 GB 140511 1:01:15 [ERROR] Plugin 'InnoDB' init function returned error. 140511 1:01:15 [ERROR] Plugin 'InnoDB' registration as a STORAGE ENGINE failed. 140511 1:01:15 [ERROR] Failed to initialize plugins. 140511 1:01:15 [ERROR] Aborting 140511 1:01:15 [Note] /usr/local/mysql/bin/mysqld: Shutdown complete 140511 01:01:15 mysqld_safe mysqld from pid file /data/mysql/yayun-mysql-server.pid ended [root@yayun-mysql-server mysql]#
而innodb 1.2.x之後版本則不會:
[root@yayun-mysql-server mysql5.6]# tail -f yayun-mysql-server.err 2014-05-11 01:06:47 5205 [Note] InnoDB: Using Linux native AIO 2014-05-11 01:06:47 5205 [Note] InnoDB: Initializing buffer pool, size = 128.0M 2014-05-11 01:06:47 5205 [Note] InnoDB: Completed initialization of buffer pool 2014-05-11 01:06:47 5205 [Note] InnoDB: Highest supported file format is Barracuda. 2014-05-11 01:06:47 5205 [Warning] InnoDB: Resizing redo log from 2*3072 to 2*327680 pages, LSN=1085681253 2014-05-11 01:06:47 5205 [Warning] InnoDB: Starting to delete and rewrite log files. 2014-05-11 01:06:47 5205 [Note] InnoDB: Setting log file ./ib_logfile101 size to 5120 MB InnoDB: Progress in MB: 100 200 300 400 500 600 700 800 900 1000 1100 1200 1300 1400 1500 1600 1700 1800 1900 2000 2100 2200 2300 2400 2500 2600 2700 2800 2900 3000 3100 3200 3300 3400 3500 3600 3700 3800 3900 4000 4100 4200 4300 4400 4500 4600 4700 4800 4900 5000 5100 2014-05-11 01:12:40 5205 [Note] InnoDB: Setting log file ./ib_logfile1 size to 5120 MB InnoDB: Progress in MB: 100 200 300 400 500 600 700 800 900 1000 1100 1200 1300 1400 1500 1600 1700 1800 1900 2000 2100 2200 2300 2400 2500 2600 2700 2800 2900 3000 3100
參考資料
http://www.mysqlperformanceblog.com/2008/11/21/how-to-calculate-a-good-innodb-log-file-size/