スロークエリログ(Slow Query Log) は処理時間の長いクエリーをログに残す機能。
今回は OS: Debian GNU/Linux Sarge & MySQL 4.1 で試してみた。
mysqld を --log-slow-queries[=file_name] オプションで起動すると、実行に long_query_time 秒より長くかかった SQL コマンドがすべてログファイルに書き込まれます。最初のテーブルロックにかかった時間は実行時間に含まれません。
(中略)
スロークエリログは、実行に時間がかかり、最適化の対象となるクエリを見つけるために使用できます。大きなログでは、これは難しい作業になります。mysqldumpslow コマンドを使用すれば、ログのクエリサマリを取得できます。
MySQL AB :: MySQL 4.1 リファレンスマニュアル :: 4.10.5 スロークエリログ
英語版のドキュメントのほうが情報量が多い → MySQL AB :: MySQL 3.23, 4.0, 4.1 Reference Manual :: 5.11.5 The Slow Query Log
MySQL AB :: MySQL 4.1 リファレンスマニュアル :: 4.6.8.4 SHOW VARIABLES によると long_query_time の初期値は 10。
・set-variable = name=value
これは、コマンドラインの --set-variable=name=value と同等。 注意: --set-variable は MySQL 4.0 で廃止された。MySQL 4.0 では、プログラム変数名をオプション名として使用できる。コマンドラインでは、--name=value を使用する。オプション設定ファイルでは、name=value を使用する。
MySQL AB :: MySQL 4.1 リファレンスマニュアル :: 4.1.2 my.cnf オプション設定ファイル
/etc/mysql/my.cnf の [mysqld] セクションに以下を追加。
# 実行時間が1秒を超えたクエリをログファイルに記録する
log-slow-queries = /var/log/mysql/mysql-slow.log
long_query_time=1
# インデックスを使用しないクエリもスロークエリログに記録する
log-queries-not-using-indexes
実際に重いクエリーを実行してから、ログを見てみる。
localhost:/home/neko# tail -10 /var/log/mysql/mysql-slow.log
# Query_time: 14 Lock_time: 0 Rows_sent: 1 Rows_examined: 1
# administrator command: Execute;
# Time: 070721 15:47:19
# User@Host: hoge[hoge] @ [127.0.0.1]
# Query_time: 14 Lock_time: 0 Rows_sent: 1 Rows_examined: 1
# administrator command: Execute;
# Time: 070721 15:47:38
# User@Host: hoge[hoge] @ [127.0.0.1]
# Query_time: 7 Lock_time: 0 Rows_sent: 1 Rows_examined: 1
# administrator command: Execute;
なんだか期待したのとちがう……
SlowLogは,テキスト形式のファイルだ。処理時間がlong-query-timeを超えたSQL文が記録される。以下のような4行で1セットだ。
# Time: 040624 1:25:24
# User@Host: [ODBC] @ localhost [127.0.0.1]
# Query_time: 5 Lock_time: 0 Rows_sent: 30670 Rows_examined: 38828
select * from city ,country ,language where country.code=city.country and city.country=language.country;
1行目 記録日時
2行目 ユーザーIDとリクエストした端末
3行目 Query_time(実行時間) Lock_time(ロック時間) Rows_sent(送信行数) Rows_examined(処理対象となった行数)
4行目 SQL文
このように設定時間を超えるSQL文が克明に記録される。
また,log-long-formatを指定していれば,インデックスを使用しなかったSQL文も記録される。Query_timeに関係なく記録されるので,見分けられるだろう。
【MySQLウォッチ】第8回 MySQLチューニングのテクニック:ITpro
やっぱり "administrator command: Execute;" というログはちょっとおかしいみたい。
「prepared statements を使ったときに、MySQL が役に立たないスロークエリーログを吐く」というバグがあるらしい。
When using prepared statements the slow query log contains no information about the statement itself, which makes it impossible to optimize statements:
(中略)
# Time: 050418 1:45:41
# User@Host: SAPMY1[SAPMY1] @ [10.17.70.89]
# Query_time: 103 Lock_time: 0 Rows_sent: 483077 Rows_examined: 483077
# administrator command: Execute;
(中略)
MySQL 4.1.14 works ok, so the bug is only in 5.
(中略)
fixed in 5.0.11
(中略)
I saw this in 4.1.10a. I'll check the logs once we upgrade to 4.1.14 or later to see if it's still happening.
MySQL Bugs: #9968: slow query log contains useless entries
これを見た感じでは、バグは修正されていると報告されつつも、4.1.14以降でもまだこの現象が出ているというコメントもある。
今回の環境は Debian GNU/Linux Sarge なので、
# COLUMNS=110 dpkg -l | grep mysql
ii libdbd-mysql-perl 2.9006-1 A Perl5 database interface to the MySQL database
ii libmysqlclient12 4.0.24-10sarge2 mysql database client library
ii libmysqlclient14 4.1.11a-4sarge7 mysql database client library
ii libmysqlclient14-dev 4.1.11a-4sarge7 mysql database development files
ii mysql-client-4.1 4.1.11a-4sarge7 mysql database client binaries
ii mysql-common-4.1 4.1.11a-4sarge7 mysql database common files (e.g. /etc/mysql/my.cnf)
ii mysql-server-4.1 4.1.11a-4sarge7 mysql database server binaries
MySQL 4.1.11 ベースなので、あきらめるしかないかな。
tags: zlashdot Database MySQL
Posted by NI-Lab. (@nilab)