2017年12月1日金曜日

コピペで試す PG10 の 3ステップレプリケーション!

本記事は PostgreSQL Advent Calendar 2017 の1日目です。
のっけから23時台の更新とひやひやさせてすみません。

■何を書くか
11/3に開催されたPostgreSQL Conforence 2017 JapanでPostgreSQLのレプリケーションに関するチュートリアルを受け持ったのですが、その準備中、PG10でレプリケーション作成の簡単さにびっくりしたのです。当然チュートリアル内でもその簡単さを熱く語ったわけですが、それを書こうと思います。

PostgreSQLレプリケーション(pgcon17j_t4) from Kosuke Kida


■PG10のレプリケーションはこうなった!
 ・パラメータのデフォルト値が変わって、簡単にレプリケーションできるようになった
 ・ロジカルレプリケーションができるようになった

 その他にも細かい話題はあるにせよ、このうち、ロジレプの陰で感動するほど簡単になったレプリケーション作成を取り上げたいと思います。

 ■ステップ0:インストール
AWSでEC2インスタンス(CentOS)にPostgreSQLをインストールします。

$ sudo yum install wget
$ wget https://download.postgresql.org/pub/repos/yum/testing/10/redhat/rhel-7-x86_64/pgdg-centos10-10-2.noarch.rpm
$ sudo rpm -ivh pgdg-centos10-10-2.noarch.rpm
$ sudo yum install postgresql10 postgresql10-server postgresql10-contrib postgresql10-devel
$ sudo vi /usr/lib/systemd/system/postgresql-10.service
---起動スクリプトのパスを変更---
# Location of database directory
# Environment=PGDATA=/var/lib/pgsql/10/data/
Environment=PGDATA=/home/postgres/data/
--
$ su - postgres
$ vi .bash_profile
---ユーザーの環境変数を変更---
### edit for PostgreSQL10
export PGDATA=/home/postgres/data
export PATH=/usr/pgsql-10/bin:.:$PATH
---

プライマリのデータベースを作成しておきます。

$ sudo systemctl start postgresql-10.service
$ sudo systemctl status postgresql-10.service
$ supostgres
$ createuser -d -r -l -P demo
$ createdb -O demo demodb
 
サンプルデータも入れておきましょう。

$ psql -U demo demodb
demodb=> create table sample (a int,b text);
demodb=> insert into sample values (1,'test1');
 
■ステップ1:プライマリ側の設定
レプリケーション用のユーザーを作成し、ユーザーのアクセス制御をpg_hba.confに書きます。
$ createuser --replication rep_user
$ vi $PGDATA/pg_hba.conf
 ----pg_hba.confを編集---
TYPE
DB
USER
CIDR-ADDRESS
METHOD
host
replication
rep_user
192.168.10.0/24
trust
host
all
rep_user
0.0.0.0/0
reject
 ---
このように、アクセス許可設定はもちろのこと、拒否設定もすると良いと思ってます。
 
レプリケーション用のパラメータを修正します。ここがポイント。デフォルト値が変更になり、(最小ではパラメータ変更なしでも)レプリケーションできます。
$ vi $PGDATA/postgresql.conf
 

パラメータ

設定

説明

listen_addresses

*

(通常はDB作成後にほぼ必須で実施)

wal_level

replica

レプリケーションに必要なWAL情報を生成

max_wal_senders

10

起動可能なwal senderプロセスの上限

max_replication_slots

10

作成可能なレプリケーションスロットの上限

synchronous_standby_names

任意

同期スタンバイの名前を指定

synchronous_commit

on

同期レベルを指定

hot_standby

on

自身がスタンバイの時に参照可能とする

hot_standby_feedback

on

自身の情報をプライマリに送信
 
自分がスタンバイになったときのために、サンプルのrecovery.confを作成しておきます。
$ vi $PGDATA/recovery.conf.node1
 
パラメータ
設定
説明
standby_mode
on
起動時にスタンバイモードになる
primary_conninfo
プライマリへの接続情報
primary_slot_name
slot2
プライマリのレプリケーションスロット名
recovery_target_timeline
latest
最新のマスターに追従する設定
 
■ステップ2:スタンバイの作成

スタンバイ側でpg_basebackupを使ってプライマリのバックアップを取得します。取得したデータはそのまま展開され、スタンバイのデータディレクトリになります。
$ pg_basebackup -U rep_user -h <node1_ip> -p 5432 -D /home/postgres/data
$ ls -ltr $PGDATA
drwx------. 3 postgres postgres    60 Oct 28 15:44 pg_wal
drwx------. 6 postgres postgres    54 Oct 28 15:44 base
drwx------. 2 postgres postgres  4096 Oct 28 15:44 global
drwx------. 2 postgres postgres    32 Oct 28 15:44 log
-rw-------. 1 postgres postgres 22844 Oct 28 15:44 postgresql.conf
-rw-------. 1 postgres postgres    88 Oct 28 15:44 postgresql.auto.conf
-rw-rw-r--. 1 postgres postgres   169 Oct 28 15:44 recovery.conf.node1
-rw-------. 1 postgres postgres  4760 Oct 28 15:44 pg_hba.conf
  :
 
スタンバイサーバーの設定もプライマリから取得したバックアップに含まれているのでほぼそのまま流用できます。変更すべき点は、recovery.confです。これはレプリケーション時にスタンバイがプライマリに接続しにいくための設定ですので、常にレプリケーションの相手ノードの情報が書いておくものだからです。
 
$ cp $PGDATA/recovery.conf.node1 $PGDATA/recovery.conf.node2
$ vi $PGDATA/recovery.conf.node2 

primary_conninfo
プライマリへの接続情報
primary_slot_name
slot1
プライマリのレプリケーションスロット名
 
この2行をプライマリへの接続情報に変更します。
 
■ステップ3:スタンバイを起動
レプリケーションスロットを使う場合、スタンバイ起動時に、必ずレプリケーションスロットを作成、または状態を確認するようにします。(レプリケーションスロットで運用する場合。)
 recovery.confに書いた primary_slot_name がまさにそのための設定で、ここで指定したスロットがマスター側に存在しないとレプリケーションできません。
 
プライマリでレプリケーションスロットを作成します。
$ su - postgres
$ psql -h <node1_ip> -U postgres postgres
postgres=# select pg_create_physical_replication_slot('slot1');
 
スタンバイでデータベースを起動します。
$ sudo systemctl start postgresql-10.service
$ su - postgres
$ ps x
11089 ?  Ss  0:00 /usr/pgsql-10/bin/postmaster -D /home/postgres/data/
11093 ?  Ss  0:00 postgres: startup process   recovering 000000010000000000000005
11097 ?  Ss  0:00 postgres: wal receiver process   streaming 0/5000140
  :
 
ほら、レプリケーションできました
 
今回は、AWSでたぶん一番簡単にPostgreSQLをインストールするところから、レプリケーションができるまでをコピペして使えるそのままのコマンドで紹介しました。
(書式がぐっちゃぐちゃで申し訳なさすぎます。見栄えはあとでコソッと変更します。)

明日は、Morihayaさんが担当してくださいます。

1 件のコメント:

PostgreSQL11のJITコンパイリングを試す

llvm-postgres 開発中のPostgreSQL11でJIT(Just In Time=実行時)コンパイリングを行い、クエリ性能の高速化を期待する新機能が登場した。 本記事では 構築方法を確認したので紹介。JITコンパイ...