全部產品
Search
文件中心

ApsaraDB RDS:尋找最耗費資源的 SQL(Top SQL)

更新時間:Jul 10, 2025

資料庫是較大型的應用,對於繁忙的資料庫,需要消耗大量的記憶體、CPU、IO 和網路資源。SQL 最佳化是資料庫最佳化的手段之一,而為了達到 SQL 最佳化的最佳效果,您首先需要瞭解最消耗資源的 SQL(Top SQL),例如 IO 消耗最高的 SQL。

資料庫資源分為多個維度,包括CPU、記憶體、IO 等,為了能夠從各個維度層面尋找最消耗資料庫資源的 SQL,您可以使用 pg_stat_statements 外掛程式統計資料庫的資源開銷和分析 Top SQL。

本文將通過樣本介紹如何建立 pg_stat_statements 外掛程式、如何分析 Top SQL 以及如何重設統計資訊。

說明

您可以開通SQL洞察和審計功能,以記錄和彙總分析SQL語句的執行情況。開啟後,該功能將自動記錄來自資料庫核心的SQL語句,以及SQL語句的執行詳情、執行帳號、IP地址等資訊,並且對執行個體效能不產生影響。

執行如下命令,在需要查詢 TOP SQL 的資料庫中,建立 pg_stat_statements 外掛程式。

CREATE EXTENSION pg_stat_statements;

pg_stat_statements 輸出內容介紹

通過查詢 pg_stat_statements 視圖,您可以得到資料庫資源開銷的統計資訊。SQL 陳述式中的一些過濾條件在 pg_stat_statements 中會被替換成變數,可以減少重複顯示的問題。

pg_stat_statements 視圖包含了一些重要訊息,例如:

  • SQL 的調用次數、總耗時、最快執行時間、最慢執行時間、平均執行時間、執行時間的方差(反映抖動),總共掃描、返回或處理了多少行。

  • shared buffer 的使用方式:命中、未命中、產生髒塊、驅逐髒塊。

  • local buffer 的使用方式:命中、未命中、產生髒塊、驅逐髒塊。

  • temp buffer 的使用方式:讀了多少髒塊、驅逐髒塊。

  • 資料區塊的讀寫時間。

下表列出了 pg_stat_statements 輸出內容中各參數的含義。

參數名稱

類型

參考

說明

userid

oid

pg_authid.oid

OID of user who executed the statement.

dbid

oid

pg_database.oid

OID of database in which the statement was executed.

queryid

bigint

Internal hash code, computed from the statement’s parse tree.

query

text

Text of a representative statement.

calls

bigint

Number of times executed.

total_time

double precision

Total time spent in the statement, in milliseconds.

min_time

double precision

Minimum time spent in the statement, in milliseconds.

max_time

double precision

Maximum time spent in the statement, in milliseconds.

mean_time

double precision

Mean time spent in the statement, in milliseconds.

stddev_time

double precision

Population standard deviation of time spent in the statement, in milliseconds.

rows

bigint

Total number of rows retrieved or affected by the statement.

shared_blks_hit

bigint

Total number of shared block cache hits by the statement.

shared_blks_read

bigint

Total number of shared blocks read by the statement.

shared_blks_dirtied

bigint

Total number of shared blocks dirtied by the statement.

shared_blks_written

bigint

Total number of shared blocks written by the statement.

local_blks_hit

bigint

Total number of local block cache hits by the statement.

local_blks_read

bigint

Total number of local blocks read by the statement.

local_blks_dirtied

bigint

Total number of local blocks dirtied by the statement.

local_blks_written

bigint

Total number of local blocks written by the statement.

temp_blks_read

bigint

Total number of temp blocks read by the statement.

temp_blks_written

bigint

Total number of temp blocks written by the statement.

blk_read_time

double precision

Total time the statement spent reading blocks, in milliseconds (if track_io_timing is enabled, otherwise zero).

blk_write_time

double precision

Total time the statement spent writing blocks, in milliseconds (if track_io_timing is enabled, otherwise zero).

分析 TOP SQL

  • 最耗 IO SQL

    • 執行如下命令,查詢單次調用最耗 IO SQL TOP 5。

      SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY (blk_read_time+blk_write_time)/calls DESC LIMIT 5;
    • 執行如下命令,查詢總最耗 I/IO 的SQL TOP 5。

      SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY (blk_read_time+blk_write_time) DESC LIMIT 5;
  • 最耗時 SQL

    • 執行如下命令,查詢單次調用最耗時 SQL TOP 5。

      SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY mean_time DESC LIMIT 5;
    • 執行如下命令,查詢總最耗時 SQL TOP 5。

      SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY total_time DESC LIMIT 5;
  • 回應時間抖動最嚴重 SQL

    執行如下命令,查詢回應時間抖動最嚴重 SQL。

    SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY stddev_time DESC LIMIT 5;
  • 最耗共用記憶體 SQL

    執行如下命令,查詢最耗共用記憶體 SQL。

    SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY (shared_blks_hit+shared_blks_dirtied) DESC LIMIT 5;
  • 最耗臨時空間 SQL

    執行如下命令,查詢最耗臨時空間 SQL。

    SELECT userid::regrole, dbid, query FROM pg_stat_statements ORDER BY temp_blks_written DESC LIMIT 5;

重設統計資訊

pg_stat_statements是累積統計,您可以通過執行如下命令,來定期清理歷史統計資訊。

SELECT pg_stat_statements_reset();

參考文檔

PostgreSQL 9.6.2 Documentation — F.29. pg_stat_statements