PostgreSQLのデータベースクラスタ内のサブディレクトリや設定ファイルの役割（3、globalの役割）

##はじめに
Dockerを使ってPostgreSQLのデータべースクラスタのサブディレクトリ・設定ファイルの役割を理解するのが目的です

##使用コンテナ
・postgres:11-alpin

PostgreSQLのデータベースクラスタのディレクトリ構成は下記のような構造になっています。

```bash
$ tree -L 1
data
├── PG_VERSION 
├── base          #データベースごとのサブディレクトリを保有するサブディレクトリ
├── global        #pg_databaseのようなクラスタで共有するテーブルを保有するサブディレクトリ
├── pg_commit_ts  #トランザクションのコミット時刻のデータを保有するサブディレクトリ
├── pg_dynshmem   #動的共有メモリサブシステムで使われるファイルを保有するサブディレクトリ
├── pg_hba.conf   #PostgreSQL に接続するクライアントの認証に関する設定を記述するファイル
├── pg_ident.conf #Ident認証のユーザー名をPostgreSQLのロール名にマッピングするためのファイル
├── pg_logical    #論理デコードのための状態データを保有するサブディレクトリ
├── pg_multixact  #マルチトランザクション状態のデータを保有するサブディレクトリ（共有行ロックで使用される）
├── pg_notify     #LISTEN/NOTIFY状態データを保有するサブディレクトリ
├── pg_replslot   #レプリケーションスロットデータを保有するサブディレクトリ
├── pg_serial     #コミットされたシリアライザブルトランザクションに関する情報を保有するサブディレクトリ
├── pg_snapshots  #エキスポートされたスナップショットを保有するサブディレクトリ
├── pg_stat       #統計サブシステム用の永続ファイルを保有するサブディレクトリ
├── pg_stat_tmp   #統計サブシステム用の一時ファイルを保有するサブディレクトリ
├── pg_subtrans   #サブトランザクションの状態のデータを保有するサブディレクトリ
├── pg_tblspc     #テーブル空間へのシンボリックリンクを保有するサブディレクトリ
├── pg_twophase   #プリペアドトランザクション用の状態ファイルを保有するサブディレクトリ
├── pg_wal        #WAL（ログ先行書き込み）ファイルを保有するサブディレクトリ
├── pg_xact       #トランザクションのコミット状態のデータを保有するサブディレクトリ  
├── postgresql.auto.conf #ALTER SYSTEMにより設定された設定パラメータを格納するのに使われるファイル
├── postgresql.conf #PostgreSQLのパラメータを設定するファイル
├── postmaster.opts #最後にサーバを起動した時のコマンドラインオプションを記録するファイル
└── postmaster.pid  #現在のpostmasterプロセスID（PID）、クラスタのデータディレクトリパス、postmaster起動時のタイムスタンプ、ポート番号、共有メモリのセグメントIDを記録するロックファイル
```

##globalの役割
globalはpg_databaseのようなクラスタで共有するテーブルを保有するサブディレクトリとなっています。
globalの役割の理解には**システムカタログ**に触れる必要があります。


###システムカタログとは
リレーショナルデータベース管理システムがテーブルや列の情報などのスキーマメタデータと内部的な情報を格納する場所です。詳細はまた別の記事にしようと思います。
globalに関係する内容としては、globalに保持されているpg_databaseはシステムカタログの一つという事です。
上記の内容に沿って説明すると、pg_databaseはデータベースクラスタ内にあるデータベースの情報が格納されている場所です。


####pg_databaseとは
ではpg_databaseについて確認していきましょう
まず、globalの中身を確認します。

```bash
#globalの中身を確認します
$ ls /var/lib/postgresql/data/global
1136              1214_fsm          1261_fsm          2397              2698              2966_vm           6000              pg_control
1136_fsm          1214_vm           1261_vm           2671              2846              2967              6000_vm           pg_filenode.map
1136_vm           1232              1262              2672              2846_vm           3592              6001              pg_internal.init
1137              1233              1262_fsm          2676              2847              3592_vm           6002
1213              1260              1262_vm           2677              2964              3593              6100
1213_fsm          1260_fsm          2396              2694              2964_vm           4060              6100_vm
1213_vm           1260_vm           2396_fsm          2695              2965              4060_vm           6114
1214              1261              2396_vm           2697              2966              4061              6115
```

下記記事のbaseの中のサブディレクトリ内と似たような構成になっていることがわかります。
つまりglobal配下にはpg_databaseのテーブルの実体が保存されているということが分かります。
[２、PG_VERSION、baseの役割](https://qiita.com/drafts/dd33d3e1e831d0d79b35/)

では実際にPostgreSQLでpg_databaseの中身を確認しましょう

```bash
$ psql -d template1 -c "SELECT * FROM pg_database;"
  datname  | datdba | encoding | datcollate |  datctype  | datistemplate | datallowconn | datconnlimit | datlastsysoid | datfrozenxid | datminmxid | dattablespace |               datacl                
-----------+--------+----------+------------+------------+---------------+--------------+--------------+---------------+--------------+------------+---------------+-------------------------------------
 postgres  |     10 |        6 | en_US.utf8 | en_US.utf8 | f             | t            |           -1 |         13116 |          562 |          1 |          1663 | 
 template1 |     10 |        6 | en_US.utf8 | en_US.utf8 | t             | t            |           -1 |         13116 |          562 |          1 |          1663 | {=c/postgres,postgres=CTc/postgres}
 template0 |     10 |        6 | en_US.utf8 | en_US.utf8 | t             | f            |           -1 |         13116 |          562 |          1 |          1663 | {=c/postgres,postgres=CTc/postgres}
(3 rows)
```
出力されている内容からpg_databaseは、今のデータベースクラスタ内に存在するデータベースの設定内容を格納しているテーブルになっている事が分かります。
上記実行結果は、template1、postgresといった特定のデータベースに接続していても同じ結果が出力されます。
**どのデータベースに接続していてもこの情報を確認する事ができるのが、globalの役割となっています。**


##余談：pg_database以外のglobal格納データ
globalの中には他にどんなテーブルが入っているのかを確認していきましょう
厳密にはglonbalに格納されている他のシステムカタログを確認します。
それについてはpg_tablesというテーブルで確認する事が可能です。

```bash
$ psql -c "SELECT * FROM pg_tables;"
schemaname          |        tablename        | tableowner | tablespace | hasindexes | hasrules | hastriggers | rowsecurity 
--------------------+-------------------------+------------+------------+------------+----------+-------------+-------------
 pg_catalog         | pg_statistic            | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_foreign_table        | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_authid               | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_user_mapping         | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_subscription         | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_largeobject          | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_type                 | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_attribute            | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_proc                 | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_class                | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_attrdef              | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_constraint           | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_inherits             | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_index                | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_operator             | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_opfamily             | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_opclass              | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_am                   | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_amop                 | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_amproc               | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_language             | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_largeobject_metadata | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_aggregate            | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_statistic_ext        | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_rewrite              | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_trigger              | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_event_trigger        | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_description          | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_cast                 | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_enum                 | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_namespace            | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_conversion           | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_depend               | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_database             | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_db_role_setting      | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_tablespace           | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_pltemplate           | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_auth_members         | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_shdepend             | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_shdescription        | postgres   | pg_global  | t          | f        | f           | f
 pg_catalog         | pg_ts_config            | postgres   |            | t          | f        | f           | f
 pg_catalog         | pg_ts_config_map        | postgres   |            | t          | f        | f           | f
```

ここで、tablespaceという列にpg_globalという値が入っているテーブルがglobalに入っているシステムカタログになっています。


##終わりに
今回のように、PostgresSQLへの操作がデータベースクラスタへどう変化を起こすかを見て行けたらと思います。

[１、ディレクトリ構造を確認](https://qiita.com/michi-michi/items/0aac8b6ccdb365269c90)
[２、PG_VERSION、baseの役割](https://qiita.com/drafts/dd33d3e1e831d0d79b35/)
３、globalの役割
[4、pg_commit_tsの役割](https://qiita.com/michi-michi/items/dc9ca80a12aa58be3cd1)
[5、pg_dynshmemの役割](https://qiita.com/michi-michi/items/5da6f480808dc6eda3f7)