「スキーマが複数ある環境で、目的のテーブルがどのスキーマにいるのか分からない」
Linuxサーバーでセルフホストしているときに、こういった状況によく遭遇します。psqlには
\dt をはじめ、スキーマ横断検索・行数・サイズまで一括で把握できるコマンドやシステムビューが揃っています。この記事では、PostgreSQLのテーブル一覧をpsqlで確認する手順を、スキーマごとの洗い出しから行数・テーブルサイズの把握まで体系的に解説します。RHEL 9.4 / Rocky Linux 9 / Ubuntu 24.04 LTS(PostgreSQL 16)で動作確認済みです。
この記事のポイント
・\dt でテーブル一覧、\dt *.* で全スキーマを一括表示できる
・\dn でスキーマ一覧を確認してから絞り込むのが現場の基本手順
・pg_stat_user_tables と pg_total_relation_size で行数とサイズを把握できる
・information_schema.tables で複数スキーマをSQL一発で洗い出せる
でも安心してください。プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
テーブル一覧を確認する場面と前提知識
PostgreSQLでは、テーブルは必ず「スキーマ」に属しています。スキーマとは名前空間のようなもので、デフォルトのpublic スキーマ以外にも、アプリケーションの設計によっては auth・sales・app のように複数のスキーマが共存することがあります。テーブル一覧を確認したい場面は主に以下のようなケースです。
・本番DBに初めてアクセスしてテーブル構造を把握するとき
・バックアップ前後のテーブル数・サイズの差分を確認するとき
・移行作業でどのテーブルが対象か洗い出すとき
・ディスク容量の圧迫原因になっているテーブルを特定するとき
\dt は psql のメタコマンド(バックスラッシュコマンド)です。SQLではなく psql が解釈するコマンドなので、セミコロン(;)は不要です。psqlでテーブル一覧を確認する基本手順
1. psqlに接続する
まず postgres ユーザーでpsqlを起動します。RHEL 9系(Rocky Linux含む)では以下の手順です。# postgres ユーザーへ切り替えてpsqlを起動する sudo -u postgres psql # 特定のDBへ直接接続する場合 sudo -u postgres psql -d mydb
psql (16.3) Type "help" for help. postgres=#
postgres=# の「postgres」は接続中のDB名です。= が通常接続、# はスーパーユーザーを示しています。別のDBに切り替えたい場合は \c dbname を使います。2. \dt でテーブル一覧を表示する
接続後に\dt を入力すると、カレントの search_path に含まれるスキーマのテーブルが一覧表示されます。\dt
List of relations Schema | Name | Type | Owner --------+-----------+-------+---------- public | customers | table | appuser public | orders | table | appuser public | products | table | appuser (3 rows)
public スキーマ以外にテーブルがある場合、デフォルトの search_path に含まれていないと \dt だけでは表示されません。この問題は後述の「スキーマを指定して絞り込む」で解消します。3. \dt+ で詳細情報を表示する
+ を付けると、テーブルのサイズや永続性(permanent/temporary)などの詳細が追加されます。\dt+
List of relations Schema | Name | Type | Owner | Persistence | Access method | Size | Description --------+-----------+-------+---------+-------------+---------------+---------+------------- public | customers | table | appuser | permanent | heap | 6416 kB | public | orders | table | appuser | permanent | heap | 24 MB | public | products | table | appuser | permanent | heap | 1024 kB | (3 rows)
pg_total_relation_size を使います。スキーマを指定して全テーブルを洗い出す
1. \dn でスキーマ一覧を確認する
まず、DBにどのスキーマが存在するかを把握します。\dn
List of schemas Name | Owner --------+------------------- auth | appuser public | pg_database_owner sales | appuser (3 rows)
auth・public・sales の3スキーマがあることが分かります。スキーマが確認できたら、次のコマンドで全テーブルを一括表示します。2. \dt *.* で全スキーマのテーブルを一覧表示する
*.*(スキーマ名.テーブル名)のパターンで全スキーマを対象にできます。# 全スキーマのテーブルを一覧表示する \dt *.* # 特定スキーマのみ絞り込む場合 \dt sales.*
List of relations Schema | Name | Type | Owner --------+---------------+-------+---------- auth | sessions | table | appuser auth | users | table | appuser public | customers | table | appuser public | orders | table | appuser public | products | table | appuser sales | campaign_logs | table | appuser sales | deals | table | appuser (7 rows)
3. information_schema.tables でSQLを使って洗い出す
psqlのメタコマンドではなく、SQL で取得したい場合はinformation_schema.tables を使います。WHERE 句で絞り込めるため、シェルスクリプトでの自動化にも向いています。SELECT table_schema, table_name, table_type FROM information_schema.tables WHERE table_schema NOT IN ('information_schema', 'pg_catalog') ORDER BY table_schema, table_name;
table_schema | table_name | table_type --------------+---------------+------------ auth | sessions | BASE TABLE auth | users | BASE TABLE public | customers | BASE TABLE public | orders | BASE TABLE public | products | BASE TABLE sales | campaign_logs | BASE TABLE sales | deals | BASE TABLE (7 rows)
table_type の値が BASE TABLE は通常テーブル、VIEW はビューです。テーブルだけを対象にするには AND table_type = 'BASE TABLE' を追加します。テーブルの行数とサイズを把握する
テーブル一覧の洗い出しに続いて、各テーブルの「規模感」も把握しておくと、バックアップ計画やチューニングの判断がしやすくなります。1. pg_stat_user_tables で行数の推定値を確認する
pg_stat_user_tables には ANALYZE 実行後の行数推定値(n_live_tup)が記録されています。VACUUM 直後でなければ実際の行数に近い値が得られます。SELECT schemaname, relname AS tablename, n_live_tup AS row_estimate FROM pg_stat_user_tables ORDER BY n_live_tup DESC;
schemaname | tablename | row_estimate ------------+---------------+-------------- public | orders | 128453 auth | sessions | 87621 public | customers | 34210 sales | campaign_logs | 15332 public | products | 4508 auth | users | 1073 sales | deals | 422 (7 rows)
SELECT count(*) FROM スキーマ.テーブル名 を実行しますが、大規模テーブルでは時間がかかるため、まずこの推定値で概観を把握するのが現場での実運用です。2. pg_total_relation_size でテーブルサイズを把握する
pg_total_relation_size は「テーブル本体 + インデックス + TOASTテーブル(大きな値の格納領域)」を合計したサイズを返します。\dt+ のSize列はテーブル本体のみなので、インデックスを含む実際のディスク占有量はこちらで確認します。SELECT schemaname, tablename, pg_size_pretty(pg_total_relation_size(schemaname || '.' || tablename)) AS total_size FROM pg_tables WHERE schemaname NOT IN ('information_schema', 'pg_catalog') ORDER BY pg_total_relation_size(schemaname || '.' || tablename) DESC;
schemaname | tablename | total_size ------------+---------------+------------ public | orders | 32 MB auth | sessions | 22 MB public | customers | 7168 kB sales | campaign_logs | 3584 kB public | products | 1280 kB auth | users | 384 kB sales | deals | 192 kB (7 rows)
3. 行数・サイズ・スキーマを1クエリでまとめて表示する
棚卸しレポートとして使いやすい、スキーマ・テーブル名・推定行数・合計サイズを1クエリで取得します。SELECT t.schemaname, t.tablename, COALESCE(s.n_live_tup, 0) AS row_estimate, pg_size_pretty(pg_total_relation_size(t.schemaname || '.' || t.tablename)) AS total_size FROM pg_tables t LEFT JOIN pg_stat_user_tables s ON t.schemaname = s.schemaname AND t.tablename = s.relname WHERE t.schemaname NOT IN ('information_schema', 'pg_catalog') ORDER BY pg_total_relation_size(t.schemaname || '.' || t.tablename) DESC;
よくあるトラブルと対処法
「\dt で何も表示されない」——search_pathの問題
\dt で Did not find any relations. と表示される場合、テーブルが public 以外のスキーマにある可能性があります。# 現在の search_path を確認する SHOW search_path; # search_path を一時的に変更してから \dt を実行する SET search_path TO sales, public; \dt # または全スキーマを対象にする \dt *.*
「Permission denied」でテーブルにアクセスできない
一覧には表示されるがデータを参照しようとするとエラーになる場合は、接続ユーザーへの権限付与を確認します。# テーブルへのアクセス権を確認する(\dp = \z と同義) \dp customers # または information_schema で確認する SELECT grantee, privilege_type FROM information_schema.role_table_grants WHERE table_name = 'customers';
GRANT SELECT ON sales.customers TO appuser; のようにスキーマ修飾で権限を付与します。n_live_tup が 0 になる
pg_stat_user_tables の n_live_tup が 0 のままの場合は、そのテーブルでまだ ANALYZE が実行されていない状態です。# 対象テーブルを手動で ANALYZE する ANALYZE VERBOSE public.orders; # またはDB全体をまとめてANALYZEする(接続は psql 外から) vacuumdb --analyze-only -d mydb -U postgres
本記事のまとめ
PostgreSQLでテーブル一覧を確認するコマンドと用途を整理します。| やりたいこと | コマンド・クエリ |
|---|---|
| カレントスキーマのテーブル一覧 | \dt |
| テーブルの詳細(サイズ・永続性) | \dt+ |
| スキーマ一覧の確認 | \dn |
| 全スキーマのテーブルを一括表示 | \dt *.* |
| 特定スキーマのみ絞り込む | \dt スキーマ名.* |
| SQLでテーブル一覧を取得する | SELECT table_name FROM information_schema.tables WHERE table_schema NOT IN (...) |
| 行数の推定値を確認する | SELECT relname, n_live_tup FROM pg_stat_user_tables ORDER BY n_live_tup DESC |
| テーブルの合計サイズを確認する | SELECT pg_size_pretty(pg_total_relation_size('スキーマ.テーブル')) |
\dt から始めてスキーマを把握し、\dt *.* で全体を洗い出したあと、pg_stat_user_tables と pg_total_relation_size で規模感を押さえる——この3ステップがLinuxサーバー上でのPostgreSQL棚卸しの基本パターンです。
PostgreSQLの運用に自信を持つには、Linuxサーバー運用の「型」が基礎になります
psqlでのテーブル棚卸しや行数・サイズの把握は、ディスク管理やプロセス管理といったOSレベルの知識があると判断の幅が広がります。独学で断片的に覚えるより、現場で実際に使われる設計パターンを一度体系的に身につけることで、PostgreSQLも含めたサーバー全体の安定運用ができるようになります。
現場で通用する安全なLinuxサーバー構築の「型」を体系的に身につけたい方へ、『Linuxサーバー構築入門マニュアル(図解60P)』を完全無料でプレゼントしています。
「独学の時間がもったいない」「プロから直接、現場の技術を最短で学びたい」という本気の方には、2日で実務レベルのスキルが身につく【初心者向けハンズオンセミナー】も開催しています。
3,100名以上が実践した「型」を無料で公開中
プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
その「型」を図解60Pにまとめた入門マニュアルを、完全無料でプレゼントしています。
姓・名・メールの3つだけ/30秒/解除は3秒 / 詳細はこちら
- 前のページへ:MariaDBをmariabackupでホットバックアップする手順|フルバックアップ・増分バックアップ・リストアの実務
- この記事の属するカテゴリ:データーベース管理へ戻る

無料メルマガで学習を続ける
Linuxの実践スキルをメールで毎週お届け。
登録は30秒、解除もいつでも可。
登録無料・いつでも解除できます