Mysql-slowlog


MySQL慢查詢日志是MySQL提供的一種日志記錄,用來記錄執行時長超過指定時長的查詢語句,具體指運行時間超過 long_query_time 值的 SQL 語句,則會被記錄到慢查詢日志中。

long_query_time 默認值是 10 ,單位是 s,即默認是 10秒 。默認情況下,MySQL數據庫並不會開啟慢查詢日志,需要手動設置這個參數。

通過慢查詢日志,可以查找出哪些查詢語句的執行效率很低,以便進行優化。一般建議開啟,它對服務器性能的影響微乎其微,但是可以記錄MySQL服務器上執行了很長時間的查詢語句。慢查詢日志可以幫助我們定位mysql性能問題所在。

MySQL慢查詢日志

慢查詢日志相關參數

slow_query_log : 是否啟用慢查詢日志,[1 | 0] 或者 [ON | OFF]

slow_query_log_file : MySQL數據庫(5.6及以上版本)慢查詢日志存儲路徑。
                    可以不設置該參數,系統則會默認給一個缺省的文件 HOST_NAME-slow.log

long_query_time : 慢查詢的閾值,當查詢時間超過設定的閾值時,記錄該SQL語句到慢查詢日志。

log_queries_not_using_indexes :設置為 ON ,可以捕獲到所有未使用索引的SQL語句(不建議啟用)

log_output : 日志存儲方式。
            log_output='FILE',表示將日志存入文件,默認值是'FILE'。      
            log_output='TABLE',表示將日志存入數據庫,這樣日志信息就會被寫入到 mysql.slow_log 表中。
            MySQL數據庫支持同時兩種日志存儲方式,配置的時候以逗號隔開即可,如:log_output='FILE,TABLE'。
            日志記錄到系統的專用日志表中,要比記錄到文件耗費更多的系統資源,因此對於需要啟用慢查詢日志,又需要能夠獲得更高的系統性能,那么建議優先記錄到文件。

5.6之前的版本,有些參數名字不一樣:

log-slow-queries : MySQL數據庫(5.6以下版本)慢查詢日志存儲路徑。

開啟日志

立即生效,重啟失效

mysql> set global slow_query_log=ON;
mysql> set global slow_query_log_file='/xxx/mysql-slow.log';

永久生效

修改 my.cnf

[mysqld]
slow_query_log           = 1
slow_query_log_file      = /xxx/mysql-slow.log
long_query_time          = 1

# 也可以寫成這種形式
slow-query-log           = 1
slow-query-log-file      = /xxx/mysql-slow.log
long-query-time          = 1

重啟mysql服務。

關閉日志

臨時關閉,重啟失效:

mysql> set global slow_query_log=OFF;

永久關閉,修改 my.cnf,重啟mysql服務:

[mysqld]
slow_query_log           = 0

MySQL慢查詢日志分析

慢查詢日志格式說明

打開慢查詢日志 mysql-slow.log ,內容都是以下格式:

# Time: 2017-11-22T12:22:32.554299Z
# User@Host: www[www] @  [192.168.10.2]  Id: 580785559
# Query_time: 24.354270  Lock_time: 0.000238 Rows_sent: 1  Rows_examined: 511156
SET timestamp=1511353352;
SELECT * FROM mo_user WHERE email = 'chxxx@hotmail.com' LIMIT 1;

其中參數說明如下:

  • log 記錄的時間:# Time: 2017-11-22T12:22:32.554299Z
  • SQL 的執行主機:# User@Host: www[www] @ [192.168.10.2] Id: 580785559
  • SQL 的執行信息(執行時間(單位:s),鎖時間,返回結果行數,查詢總行數):# Query_time: 24.354270 Lock_time: 0.000238 Rows_sent: 1 Rows_examined: 511156;
  • SQL 執行發生的時間:SET timestamp=1511353352;
  • SQL 的執行內容:SELECT * FROM mo_user WHERE email = 'chxxx@hotmail.com' LIMIT 1;

mysqldumpslow

mysqldumpslow 是MySQL自帶的慢查詢日志分析工具(perl腳本)。執行命令 mysqldumpslow --help,顯示命令參數如下:

Usage: mysqldumpslow [ OPTS... ] [ LOGS... ]

Parse and summarize the MySQL slow query log. Options are

  --verbose    verbose
  --debug      debug
  --help       write this text to standard output

  -v           verbose
  -d           debug
  -s ORDER     what to sort by (al, at, ar, c, l, r, t), 'at' is default
                al: average lock time
                ar: average rows sent
                at: average query time
                 c: count
                 l: lock time
                 r: rows sent
                 t: query time
  -r           reverse the sort order (largest last instead of first)
  -t NUM       just show the top n queries
  -a           don't abstract all numbers to N and strings to 'S'
  -n NUM       abstract numbers with at least n digits within names
  -g PATTERN   grep: only consider stmts that include this string
  -h HOSTNAME  hostname of db server for *-slow.log filename (can be wildcard),
               default is '*', i.e. match all
  -i NAME      name of server instance (if using mysql.server startup script)
  -l           don't subtract lock time from total time

參數說明:

  • -v、--verbose : 在詳細模式下運行,打印有關該程序的更多信息。

  • -d、--debug : 在調試模式下運行。

  • --help : 顯示幫助信息並退出程序

  • -s [sort_type] : sort_type 是信息排序的依據

    al:average lock time,按平均等待鎖的時間排序
    ar:average rows sent,按平均發給客戶端的行總數排序
    at:average query time,按平均查詢時間排序
    c:count,按出現總次數排序
    l:lock time,按等待鎖的時間排序
    r:rows sent,按掃描的行總數排序
    t:query time,按累計總耗費時間排序

  • -r : 倒序信息排序

  • -t NUM: 只顯示前 n 個查詢,降序

  • -a : 不把數字抽象為'N',不把字符串抽象為'S'

  • -n NUM : 「abstract numbers with at least n digits within names」

  • -g PATTERN : 根據字符串篩選慢查詢日志,可寫正則匹配,大小寫不敏感。

  • -h HOSTNAME : 根據服務器名稱選擇慢查詢日志

  • -i NAME : 根據服務器 MySQL 實例名稱選擇慢查詢日志

  • -l : 不要將總時間減去鎖定時間

mysqldumpslow 分析的結果如下:

  • Count : 出現次數(Count)
  • Time : 執行最長時間(Time) 和 累計總耗費時間(Time)
  • Lock : 等待鎖的時間(Lock)
  • Rows : 發送給客戶端的行總數(Rows) 和 掃描的行總數(Rows)
  • root[root]@localhost : 用戶
  • SHOw FULL ... : SQL語句本身(抽象了格式, 比如 limit 1, 20 用 limit N,N 表示。'N'表示數字,'S'表示字符串)。

例子:
返回記錄數最多的10個SQL

mysqldumpslow -s r -t 10 mysql-slow.log

mysqlsla

mysqlsla是 hackmysql.com 推出的一款日志分析工具(該網站還維護了 mysqlreport, mysqlidxchk 等比較實用的mysql工具)
整體來說, 功能非常強大。數據報表,非常有利於分析慢查詢的原因, 包括執行頻率, 數據量, 查詢消耗等。

但是,hackmysql.com官方已經在2015年1月份放棄了對mysqlsla的維護。

安裝

解決依賴關系

# yum install  perl-DBI perl-DBD-MySQL 

可能會遇到的問題:Can't locate ExtUtils/MakeMaker.pm,解決如下:

# yum install  perl-ExtUtils-CBuilder  perl-ExtUtils-MakeMaker

可能會遇到的問題:Can't locate Time/HiRes.pm in @INC,解決如下:

# yum install perl-Time-HiRes

下載mysqlsla

當前 mysqlsla 的最新版本為 2.03,到官網下載(官方鏈接已經失效),可以去這個 有效下載地址 下載。

編譯安裝

# tar xvfz mysqlsla-2.03.tar.gz 
# cd mysqlsla-2.03
# perl Makefile.PL
# make
# make install

使用

# mysqlsla -lt slow mysql-slow.log 

或者 
# mysqlsla -lt slow mysql-slow.log -sf "+SELECT" -db dbName -top 10 -sort t_sum

參數意義 :

  • -lt :表示日志類型,有: slow, general, binary, msl, udl
  • -sf :[+-][TYPE],包括|不包括,過濾sql語句的類型 [TYPE]有 SELECT, CREATE, DROP, UPDATE, INSERT,例如 "+SELECT,INSERT",不出現的默認是 - ,即不包括。
  • -db :要處理哪個庫的日志。
  • -top :表示取按規則排序的前多少條。
  • -sort :按某種規則排序,t_sum 按總時間排序, c_sum 按總次數排序。c_sum_p : sql語句執行次數占總執行次數的百分比。

對慢查詢日志文件的分析,最簡化的調用方式如下:

# mysqlsla -lt slow [SlowLogFilePath] > [ResultFilePath]

格式說明如下:

  • 總查詢次數 (queries total), 去重后的sql數量 (unique)
  • 輸出報表的內容排序方式(sorted by)
  • 最重大的慢sql統計信息, 包括平均執行時間, 等待鎖時間, 結果行的總數, 掃描的行總數。

  • Count: sql的執行次數及占總的slow log數量的百分比.
  • Time:執行時間, 包括總時間, 平均時間, 最小, 最大時間, 時間占總慢sql時間的百分比.
  • 95% of Time:去除最快和最慢的sql, 覆蓋率占95%的sql的執行時間.
  • Lock Time:等待鎖的時間.
  • 95% of Lock :95%的慢sql等待鎖時間.
  • Rows sent:結果行統計數量, 包括平均, 最小, 最大數量.
  • Rows examined: 掃描的行數量.
  • Database:屬於哪個數據庫
  • Users:哪個用戶,IP, 占到所有用戶執行的sql百分比

  • Query abstract:抽象后的sql語句
  • Query sample:sql語句個例

pt-query-digest

percona-toolkit 工具介紹

percona-toolkit 是一組高級命令行工具的集合,用來執行各種通過手工執行非常復雜和麻煩的mysql和系統任務。這些任務包括:

  • 檢查master和slave數據的一致性
  • 有效地對記錄進行歸檔
  • 查找重復的索引
  • 對服務器信息進行匯總
  • 分析來自日志和tcpdump的查詢
  • 當系統出問題的時候收集重要的系統信息

Percona Toolkit整個工具箱提供了非常多實用的工具,具體的使用方法可以參看 官方文檔

percona-toolkit安裝

安裝 percona-toolkit 非常簡單,到 官網 下載 .tar.gz 包:

# wget percona.com/get/percona-toolkit.tar.gz
# tar -zxvf percona-toolkit-2.2.5.tar.gz

然后依次執行下面的命令:

# perl Makefile.PL
# make
# make install

默認的會被安裝在 /usr/local/bin 目錄下。執行 man percona-toolkit 可以查看安裝了哪些工具。

運行工具可能會遇到下面的錯誤:


這是因為缺少相應包,.pm包實際上是perl的包,運行下面的命令安裝即可:

yum install -y perl-Time-HiRes

如果安裝過程中出現 Error Downloading Packages 錯誤,嘗試 yum clean all 后再安裝。使用其Percona Toolkit中其他工具也可能會遇到類似的問題,按照提示安裝相應的perl包就可以了。

問題:Can't locate Digest/MD5.pm in @INC
解決:# yum install perl-Digest-MD5

問題:Can't locate ExtUtils/MakeMaker.pm in @INC
解決:# yum install perl-ExtUtils-CBuilder perl-ExtUtils-MakeMaker

pt-query-digest使用

pt-query-digest 可以從普通MySQL日志,慢查詢日志以及二進制日志中分析查詢,甚至可以從 SHOW PROCESSLIST; 和MySQL協議的tcpdump中進行分析,如果沒有指定文件,它從標准輸入流(STDIN)中讀取數據。

最簡單的用法如下:

# pt-query-digest mysql-slow.log

輸出信息大致如下:

整個輸出分為三大部分:

整體概要(Overall)

這個部分是一個大致的概要信息(類似loadrunner給出的概要信息),通過它可以對當前MySQL的查詢性能做一個初步的評估,比如各個指標的最大值(max),平均值(min),95%分布值,中位數(median),標准偏差(stddev)。
這些指標有查詢的執行時間(Exec time),鎖占用的時間(Lock time),MySQL執行器需要檢查的行數(Rows examine),最后返回給客戶端的行數(Rows sent),查詢的大小。

查詢的匯總信息(Profile)

這個部分對所有 "重要" 的查詢(通常是比較慢的查詢)做了個一覽表:


每個查詢都有一個Query ID,這個ID通過Hash計算出來的。pt-query-digest 是根據這個所謂的Fingerprint來group by的。舉例下面兩個查詢的Fingerprint是一樣的都是 select * from table1 where column1 = ?,工具箱中也有一個與之相關的工具 pt-fingerprint

select * from table1 where column1 = 2
select * from table1 where column1 = 3
  • Rank整個分析中該“語句”的排名,一般也就是性能最常的。
  • Response time “語句”的響應時間以及整體占比情況。
  • Calls 該“語句”的執行次數。
  • R/Call 每次執行的平均響應時間。
  • V/M 響應時間的差異平均對比率。

在尾部有一行輸出,顯示了其他2個占比較低而不值得單獨顯示的查詢的統計數據。

詳細信息

這個部分會列出Profile表中每個查詢的詳細信息:(默認是按照總的Exec time排序,降序)

包括Overall中有的信息、查詢響應時間的分布情況以及該查詢 "入榜" 的理由,最底下會顯示該查詢SQL語句(真實顯示,非抽象格式)。

pt-query-digest 還有很多復雜的操作,這里就不一一介紹了。比如:從PROCESSLIST中查詢某個MySQL中最慢的查詢:

# pt-query-digest –processlist h=host1

從tcpdump中分析:

# tcpdump -s 65535 -x -nn -q -tttt -i any -c 1000 port 3306 > mysql.tcp.txt
# pt-query-digest --type tcpdump mysql.tcp.txt

從一台機器上將 slow log 保存到另外一台機器上待稍后詳細分析:

# pt-query-digest --review h=host2 --no-report slow.log

還可以跟一些過濾條件。詳見 官方文檔

另外結合一些第三方工具還能生成相應的報表,可以 參考這里

建議 :當 slow log 很大的時候最好還是將日志文件移到其他機器上進行分析,避免分析時過度消耗該服務器資源。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM