1. ホーム
  2. database

pg_restore error: role XXX does not exist

2023-08-25 11:02:25

質問

あるシステムから別のシステムにデータベースを複製しようとしています。関係するバージョンは 9.5.0 (ソース) と 9.5.2 (ターゲット) です。

ソース DB 名は foodb で、オーナーは pgdba で、ターゲットのDB名は foodb_dev という名前になり、オーナーは pgdev .

すべてのコマンドはレプリカをホストするターゲットシステム上で実行されます。

このコマンドは pg_dump コマンドは

    pg_dump -f schema_backup.dump --no-owner -Fc -U pgdba -h $PROD_DB_HOSTNAME -p $PROD_DB_PORT -d foodb -s --clean;

これはエラーなく実行されます。

対応する pg_restore

    pg_restore --no-owner --if-exists -1 -c -U pgdev -d foodb_dev schema_backup.dump

というエラーになります。

pg_restore: [archiver (db)] Error while PROCESSING TOC:
pg_restore: [archiver (db)] Error from TOC entry 3969; 0 0 ACL public pgdba
pg_restore: [archiver (db)] could not execute query: ERROR:  role "pgdba" does not exist
Command was: REVOKE ALL ON SCHEMA public FROM PUBLIC;
REVOKE ALL ON SCHEMA public FROM pgdba;
GRANT ALL ON SCHEMA public TO pgdba;
GRANT ...

ダンプファイルをプレーンテキスト形式で生成した場合 ( -Fp ) のようないくつかのエントリが含まれていることがわかります。

REVOKE ALL ON TABLE dump_thread FROM PUBLIC;
REVOKE ALL ON TABLE dump_thread FROM pgdba;
GRANT ALL ON TABLE dump_thread TO pgdba;
GRANT SELECT ON TABLE dump_thread TO readonly;

に権限を設定しようとするものです。 pgdba のみを持つターゲットシステムにはもちろんユーザとして存在しません。 pgdev のみであり、したがって pg_restore .

ソースDB上では、例えば dump_thread テーブルを使用することができます。

# \dp+ dump_thread
Access privileges
-[ RECORD 1 ]-----+--------------------
Schema            | public
Name              | dump_thread
Type              | table
Access privileges | pgdba=arwdDxt/pgdba+
                  | readonly=r/pgdba
Column privileges |
Policies          |

手っ取り早い解決策は、単にユーザー pgdba をターゲットクラスタに追加して終了です。

しかし --no-owner は、そもそもオーナー固有のコマンドをダンプに含めないように注意する必要があるのでは?

どのように解決するのですか?

私は --no-owner-x . 私は -x をすべての pg_dump コマンドに変換する、ということです。

-x, --no-privileges          do not dump privileges (grant/revoke)

これは、事実上、問題のある GRANT / REVOKE コマンドをダンプから取得します。問題は解決されました。