これはPGroonga 2.X and 3.X用のドキュメントです。古いPGroongaを使っているならPGroonga 1.xのドキュメントを見てください。

ストリーミングレプリケーション

PGroongaは1.1.6からPostgreSQL組み込みのWALベースのストリーミングレプリケーション機能をサポートしています。

PGroonga 3.2.1以降とPostgreSQL 15以降を使っている場合はWALリソースマネージャーを使ったストリーミングレプリケーションの方がオススメです。

PGroongaのWALは以下のようにスタンバイのサーバーへ送信されます。

sequenceDiagram
    box transparent Primary
        participant Primary user
        participant Primary PGroonga
        participant WAL sender
    end
    box transparent Standby
        participant WAL receiver
        participant Standby user
        participant Standby PGroonga
    end

    Primary user->>+Primary PGroonga:INSERT/UPDATE/DELETE
    Note right of Primary PGroonga:Write WAL
    Primary PGroonga->>+WAL sender:Notify write WAL
    WAL sender->>+WAL receiver:Send WAL
    Note right of WAL receiver:Save WAL
    Standby user->>+Standby PGroonga:SELECT
    Note right of Standby PGroonga:Apply saved WAL

WALをサポートしているといってもクラッシュセーフではないことに注意してください。WALベースのストリーミングレプリケーションをサポートしているだけです。もし、PGroongaのインデックスを更新している最中にPostgreSQLがクラッシュしたら、そのPGroongaのインデックスは壊れるかもしれません。もし、PGroongaのインデックスが壊れたらREINDEXで作り直さなければいけません。

参考:クラッシュセーフ

このドキュメントではPostgreSQL組み込みのWALベースのストリーミングレプリケーション機能をPGroonga用に設定する方法を説明します。多くの手順は通常のストリーミングレプリケーションの設定手順です。いくつかPGroonga固有の手順があります。

概要

PostgreSQL組み込みのWALベースのストリーミングレプリケーション機能をPGroonga用に設定する手順は次の通りです。「[通常]」タグは通常のストリーミングレプリケーション用の手順であることを示しています。「[固有]」タグはPGroonga固有の手順であることを示しています。

  1. [通常] プライマリーとスタンバイでPostgreSQLをインストールする

  2. [固有] プライマリーとスタンバイでPGroongaをインストールする

  3. [通常] プライマリーでストリーミングレプリケーション用にPostgreSQLを設定する

  4. [固有] プライマリーでPGroonga用にPostgreSQLを設定する

  5. [通常] プライマリーでデータを追加する

  6. [固有] プライマリーでPGroongaのインデックスを作る

  7. [固有] プライマリーでPGroonga関連のデータを書き出す

  8. [通常] スタンバイでpg_basebackupを実行する

  9. [固有] スタンバイでPGroonga用にPostgreSQLを設定する

  10. [通常] スタンバイでPostgreSQLを起動する

例で使う環境

このドキュメントでは次の環境を使います。

このドキュメントではUbuntu 22.04用のコマンドラインを書いています。もし、他のプラットフォームを使っている場合は自分でコマンドラインを調整してください。

[通常] プライマリーとスタンバイでPostgreSQLをインストールする

これは通常の手順です。

プライマリーとスタンバイでPostgreSQL 15をインストールします。

sudo apt install -y gpg lsb-release wget
wget --quiet -O - https://www.postgresql.org/media/keys/ACCC4CF8.asc | sudo gpg --no-default-keyring --keyring /usr/share/keyrings/pdgd-keyring.gpg --import -
echo "deb [signed-by=/usr/share/keyrings/pdgd-keyring.gpg] http://apt.postgresql.org/pub/repos/apt/ $(lsb_release -cs)-pgdg main" | sudo tee /etc/apt/sources.list.d/pgdg.list
sudo apt update
sudo apt install -y postgresql-15

[固有] プライマリーとスタンバイでPGroongaをインストールする

これはPGroonga固有の手順です。

プライマリーとスタンバイでPGroongaをインストールします。

sudo apt install -y software-properties-common
sudo add-apt-repository -y universe
sudo add-apt-repository -y ppa:groonga/ppa
sudo apt install -y wget lsb-release
wget https://packages.groonga.org/ubuntu/groonga-apt-source-latest-$(lsb_release --codename --short).deb
sudo apt install -y -V ./groonga-apt-source-latest-$(lsb_release --codename --short).deb
sudo apt update
sudo apt install -y -V postgresql-15-pgdg-pgroonga

[通常] プライマリーでストリーミングレプリケーション用にPostgreSQLを設定する

これは通常の手順です。

プライマリーでだけ次のストリーミングレプリケーション用の設定をpostgresql.confに追加します。

多くのスタンバイがいる場合はmax_wal_sendersも設定する必要があります。max_wal_sendersのデフォルト値は10です。スタンバイ2台では10で十分です。

PostgreSQL:ドキュメント:レプリケーションも参照してください。

/etc/postgresql/15/main/postgresql.conf:

変更前:

#listen_addresses = 'localhost'

変更後:

listen_addresses = 'localhost,192.168.0.30'

プライマリーでだけ以下のストリーミングレプリケーション用の設定をpg_hba.confに追加します。

/etc/postgresql/15/main/pg_hba.conf:

変更前:

local   replication     all                                     peer
host    replication     all             127.0.0.1/32            scram-sha-256
host    replication     all             ::1/128                 scram-sha-256

変更後:

local   replication     all                                     peer
host    replication     all             127.0.0.1/32            scram-sha-256
host    replication     all             ::1/128                 scram-sha-256
host    replication     all             192.168.0.0/24          scram-sha-256

プライマリーでだけレプリケーションユーザーを作成します。

$ sudo -u postgres -H createuser --pwprompt --replication replicator
Enter password for new role: (passw0rd)
Enter it again: (passw0rd)

[固有] プライマリーでPGroonga用にPostgreSQLを設定する

これはPGroonga固有の手順です。

PGroongaのWAL関連の設定とクラッシュセーフ関連の設定を追加する必要があります。

PGroongaのWAL用には、pgronga.enable_walパラメーターpgroonga.max_wal_sizeパラメーターを設定する必要があります。

クラッシュセーフ用には、pgroonga_crash_saferモジュールshared_preload_librariesパラメーターに追加してpgroonga.crash_safe = onも追加する必要があります。

注意:pgroonga_crash_saferモジュールを使うと書き込み性能が低下します。メンテナンス性と性能のトレードオフがあります。最大の書き込み性能が必要な場合はこのモジュールを使えません。このトレードオフについてはクラッシュセーフも参照してください。

/etc/postgresql/15/main/postgresql.conf:

変更前:

#shared_preload_libraries = ''

変更後:

shared_preload_libraries = 'pgroonga_crash_safer'

/etc/postgresql/15/main/conf.d/pgroonga.conf:

pgroonga.enable_wal = on
pgroonga.max_wal_size = 100MB
pgroonga.enable_crash_safe = on

書き込みが激しいシステムではpgroonga.max_wal_sizeの値をもっと大きくしないといけないかもしれません。

pgroonga_crash_saferモジュールを使わない場合は、shared_preload_librariesからpgroonga_crash_saferを除いて、pgroonga.enable_crash_safe = onも消します。

この設定を反映するためにPostgreSQLを再起動します。

sudo -H systemctl restart postgresql

[通常] プライマリーでデータを挿入する

これは通常の手順です。

プライマリーでだけ一般ユーザーを作成します。

sudo -u postgres -H createuser ${USER}

プライマリーでだけデータベースを作成します。

sudo -u postgres -H createdb --template template0 --locale C --encoding UTF-8 --owner ${USER} blog

プライマリーでだけ作成したデータベースにテーブルを追加します。

作成したblogデータベースに接続します。

psql blog

entriesテーブルを作成します。

CREATE TABLE entries (
  title text,
  body text
);

作成したentriesテーブルにデータを追加します。

INSERT INTO entries VALUES ('PGroonga', 'PGroonga is a PostgreSQL extension for fast full text search that supports all languages. It will help us.');
INSERT INTO entries VALUES ('Groonga', 'Groonga is a full text search engine used by PGroonga. We did not know about it.');
INSERT INTO entries VALUES ('PGroonga and replication', 'PGroonga 1.1.6 supports WAL based streaming replication. We should try it!');

[固有] プライマリーでPGroongaのインデックスを作成する

これはPGroonga固有の手順です。

このデータベースにPGroongaをインストールします。スーパーユーザー権限が必要です。

sudo -u postgres -H psql blog --command "CREATE EXTENSION pgroonga;"
sudo -u postgres -H psql blog --command "GRANT USAGE ON SCHEMA pgroonga TO ${USER};"

再度一般ユーザーでPostgreSQLに接続します。

psql blog

プライマリーでPGroongaのインデックスを作成します。

CREATE INDEX entries_full_text_search ON entries USING pgroonga (title, body);

作成したインデックスを確認します。

SET enable_seqscan TO off;
SELECT title FROM entries WHERE title &@~ 'replication';
--           title           
-- --------------------------
--  PGroonga and replication
-- (1 row)

[固有] プライマリーでだけPGroonga関連のデータをフラッシュする

これはPGroonga固有の手順です。

プライマリーでだけメモリー上にあるPGroonga関連のデータを確実にディスクに書き出します。以下のどれかの方法を使います。

  1. SELECT pgroonga_command('io_flush');を実行する

  2. すべての接続を切断する

pgroonga_command('io_flush')を使う場合は次のようになります。

SELECT pgroonga_command('io_flush') AS command;
--                     command                    
-- -----------------------------------------------
--  [[0,1478446349.2241,0.1413860321044922],true]
-- (1 row)

プライマリーでは、次のpg_basebackupの手順が終わるまではPGroongaのインデックスを使っているテーブルを変更してはいけません。

[通常] スタンバイでpg_basebackupを実行する

これは通常の手順です。

スタンバイでだけpg_basebackupを実行します。pg_basebackupはプライマリーから現在のデータベースをコピーします。

スタンバイ:

$ sudo -H systemctl stop postgresql
$ sudo -u postgres -H rm -rf /var/lib/postgresql/15/main
$ sudo -u postgres -H pg_basebackup --host 192.168.0.30 -D /var/lib/postgresql/15/main --progress -U replicator -R
Password: (passw0rd)
175007/175007 kB (100%), 1/1 tablespace

[固有] スタンバイでPGroonga用にPostgreSQLを設定する

これはPGroonga固有の手順です。

2.4.2で追加。

次のモジュールをshared_preload_librariesパラメーターに追加します。

注意:pgroonga_crash_saferモジュールを使うと書き込み性能が低下します。メンテナンス性と性能のトレードオフがあります。最大の書き込み性能が必要な場合はこのモジュールを使えません。このトレードオフについてはクラッシュセーフも参照してください。

スタンバイ:

/etc/postgresql/15/main/postgresql.conf:

変更前:

#shared_preload_libraries = ''

変更後:

shared_preload_libraries = 'pgroonga_standby_maintainer,pgroonga_crash_safer'

スタンバイ:

/etc/postgresql/15/main/conf.d/pgroonga.conf:

pgroonga.enable_wal = on
pgroonga.enable_crash_safe = on

pgroonga_crash_saferモジュールを使わない場合は、shared_preload_librariesからpgroonga_crash_saferを除いて、pgroonga.enable_crash_safe = onも消します。

[通常] スタンバイでPostgreSQLを起動する

これは通常の手順です。

スタンバイでPostgreSQLを起動します。

sudo -H systemctl start postgresql

これで、プライマリーで挿入したデータをプライマリーで作成したPGroongaのインデックスで検索できます。

スタンバイ1:

psql blog
SET enable_seqscan TO off;
SELECT title FROM entries WHERE title &@~ 'replication';
--           title           
-- --------------------------
--  PGroonga and replication
-- (1 row)

pg_basebacup以降にプライマリーで追加したデータも検索できます。

プライマリー:

INSERT INTO entries VALUES ('PostgreSQL 9.6 and replication', 'PostgreSQL supports generic WAL since 9.6. It is required for replication for PGroonga.');

スタンバイ1:

SELECT title FROM entries WHERE title &@~ 'replication';
--              title              
-- --------------------------------
--  PGroonga and replication
--  PostgreSQL 9.6 and replication
-- (2 rows)

スタンバイ2:

psql blog
SET enable_seqscan TO off;
SELECT title FROM entries WHERE title &@~ 'replication';
--              title              
-- --------------------------------
--  PGroonga and replication
--  PostgreSQL 9.6 and replication
-- (2 rows)