/var/lib/mysql/mysql-slow.log { create 644 mysql mysql notifempty daily rotate 30 missingok compress delaycompress dateext sharedscripts postrotate # just if mysqld is really running if test -x /usr/bin/mysqladmin && \ /usr/bin/mysqladmin ping &>/dev/null then /usr/bin/mysqladmin flush-logs fi endscript }
# A software update is available: # * Percona Toolkit 2.2.6 has a possible security issue (CVE-2014-2029) upgrade is recommended. The current version for Percona::Toolkit is 2.2.10.
# 5.3s user time, 80ms system time, 28.53M rss, 216.25M vsz # Current date: Thu Aug 28 21:42:16 2014 # Hostname: hoge-db03 # Files: /var/lib/mysql/mysql-slow.log # Overall: 10.48k total, 57 unique, 0.16 QPS, 0.05x concurrency __________ # Time range: 2014-08-28 03:40:02 to 21:42:15 # Attribute total min max avg 95% stddev median # ============ ======= ======= ======= ======= ======= ======= ======= # Exec time 3002s 100ms 11s 286ms 777ms 284ms 180ms # Lock time 1s 41us 378us 96us 119us 16us 98us # Rows sent 13.66M 1 174.31k 1.33k 6.31k 5.51k 0.99 # Rows examine 825.18M 2.00k 1.46M 80.61k 211.82k 110.61k 36.57k # Query size 5.05M 154 791 504.95 755.64 100.54 487.09
# Query 1: 0.06 QPS, 0.02x concurrency, ID 0x3BEFCC5114487A23 at byte 3388347 # This item is included in the report because it matches --limit. # Scores: V/M = 0.36 # Time range: 2014-08-28 03:40:02 to 21:41:41 # Attribute pct total min max avg 95% stddev median # ============ === ======= ======= ======= ======= ======= ======= ======= # Count 40 4211 # Exec time 42 1269s 100ms 11s 301ms 777ms 327ms 180ms # Lock time 42 426ms 50us 253us 101us 119us 12us 98us # Rows sent 0 4.11k 1 1 1 1 0 1 # Rows examine 23 197.02M 3.36k 847.55k 47.91k 130.04k 51.64k 30.09k # Query size 39 2.00M 492 498 497.70 487.09 0 487.09 # String: # Databases hoge # Hosts # Users hoge # Query_time distribution # 1us # 10us # 100us # 1ms # 10ms # 100ms ################################################################ # 1s ## # 10s+ # # Tables # SHOW TABLE STATUS FROM `database` LIKE 'tablename'\G # SHOW CREATE TABLE `database`.`tablename`\G # EXPLAIN /*!50100 PARTITIONS*/ select hoge, fuga from tablename where ( hoge = 1 and fuga = 2 and hogehoge = 3 ) order by upd_datetime DESC\G
クエリを解析する
ようやくExplainの出番です。対象のクエリの先頭に"EXPLAIN"をつけて解析します。
EXPLAIN SELECT hoge, count(fuga) from xxxxxxxxxxx_8 where id = 4 and upd_date < 1408647600000 group by hoge; +----+-------------+-------------------+-------+---------------+---------+---------+------+---------+-------------+ | id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra | +----+-------------+-------------------+-------+---------------+---------+---------+------+---------+-------------+ | 1 | SIMPLE | xxxxxxxxxxx_8 | index | NULL | PRIMARY | 12 | NULL | 4857810 | Using where | +----+-------------+-------------------+-------+---------------+---------+---------+------+---------+-------------+ 1 row in set (0.00 sec)
インデックスの基本はWHERE句の順番どおりに作成します。この場合であれば(col1,col2)です。ただし、既にcol1からはじまる別のインデックスを利用していてcol2のカーディナリティが低い場合、もしくはcol1のカーディナリティが高かったりユニークな値の場合は既に絞りきっているため効果は薄いです。WHERE句がそのあともcol3 = z AND col4 = …と続く場合も含めて、rowsの値がちゃんと減っているか確認しながら適切なカラムまで指定します。
mysql> SELECT ... WHERE col1 = x ORDER BY col2;
ORDER BY句があるときに適切なインデックスがないとUsing filesortが出ます。基本は順番通り(col1,col2)で作成します。
mysql> SELECT ... WHERE col1 = x ORDER BY col2 LIMIT 10;