PostgreSQL EXPLAIN アナライザー

EXPLAIN (ANALYZE, BUFFERS, FORMAT JSON) の JSON プランを貼り付けると、ツリーとローカルで判定できるホットスポットを表示します。解析はブラウザー内で行われ、クエリは実行されず、データベースにも接続しません。

ブラウザ内でローカルに実行
このツールはすべてのデータをブラウザー内で処理します。
EXPLAIN JSONJSON の結果を貼り付けてください。データベースに接続されることはありません。

EXPLAIN JSON から PostgreSQL の実行プランを読む手順

EXPLAIN (ANALYZE, BUFFERS, FORMAT JSON) の JSON 出力を貼り付け、「プランを解析」を押します。ページはプランのツリーを描画し、ノード数・コスト・実測時間・行数を集計して、ローカルで判定できるホットスポットを一覧にします。

プランはブラウザー内で解析され、SQL は実行されず、データベースやこのサイトへ何も送信されません。読み取るのは JSON 形式のみで、psql のテキスト形式は代用できません。

  1. EXPLAIN (ANALYZE, BUFFERS, FORMAT JSON) でクエリを実行します。ANALYZE を付けないと実測の行数・時間がなく比較できません。
  2. 結果全体(外側の配列のままで構いません)を入力欄に貼り付け、「プランを解析」を押します。
  3. まず概要を確認します。ノード数、最大の合計コスト、実行時間、ルート ノードが返した行数です。
  4. 検出一覧を確認します。推定のずれ、フィルタで除外された行、多数回実行された内側、最も遅いノードが対応すべき項目です。
  5. 一度に 1 つだけ直し(インデックス、書き換え、統計目標)、同じ条件でプランを再取得して数値が動くか確認します。

解析が報告する内容、見えない範囲、結果の使い方

解析が報告する内容

概要にはノード数、ツリー内の最大 Total Cost、実行時間(Execution Time があればそれを使用し、なければ最も遅いノード)、ルート ノードの行数が表示されます。下のツリーは各ノードのコスト、実測時間、行数、ループ回数、推定値、インデックス条件またはフィルタを並べます。

検出一覧は Plan Rows と実際に返された行数を比較し、10 倍以上ずれていれば両方の数値とともにノード名を挙げます。ほかに、返した行数の 10 倍以上をフィルタで除外したノード、1000 回以上実行された内側、50 ms 以上かつ実行時間の 5 分の 1 以上を占める最も遅いノードも報告します。

見えない範囲

ANALYZE なしのプランには実測の行数も時間もないため、ページはその旨を表示し、0 を表示する代わりに時間の指標を省略します。推定値の検査も同じ理由で行いません。BUFFERS の数値は JSON に含まれますがここでは解釈せず、JIT、並列ワーカー間の配分、トリガーや関数の時間も解析しません。

1 つのプランは 1 回の実行に対応します。暖まったキャッシュ、異なる統計、別のパラメーター値、汎用プランを再利用するプリペアド ステートメントではツリーが変わります。同じ条件で取得したプランを比較し、検出結果は判断ではなく確認すべき手がかりとして扱ってください。

結果をどう活かすか

推定の大きなずれは、統計が古いか、プランナーが推定できない条件(列に関数を使う、相関のある条件、偏った分布)を示すことが多く、ANALYZE、統計目標の引き上げ、条件の書き換えでインデックスを触る前にプランが変わることがあります。

フィルタで除外された行は、欠けているか使われていないインデックスと選択性の低い条件を示します。ネステッド ループの内側が繰り返し実行される場合は、ハッシュ結合の方が適する結合の典型的な兆候です。1 つ変更し、同じパラメーターで再実行し、実際の負荷で勝つプランを採用してください。

最近使ったツール: