PostgreSQLで読み取り専用ユーザーを作成するにはどうすればよいですか?


420

特定のデータベースからのみSELECTを実行できるユーザーをPostgreSQLで作成したいと思います。MySQLでは、コマンドは次のようになります。

GRANT SELECT ON mydb.* TO 'xxx'@'%' IDENTIFIED BY 'yyy';

PostgreSQLの同等のコマンドまたは一連のコマンドは何ですか?

私は試した...

postgres=# CREATE ROLE xxx LOGIN PASSWORD 'yyy';
postgres=# GRANT SELECT ON DATABASE mydb TO xxx;

ただし、データベースに付与できるのは、CREATE、CONNECT、TEMPORARY、TEMPのみです。

回答:


641

単一のテーブルに使用/選択を許可する

データベースへのCONNECTのみを付与する場合、ユーザーは接続できますが、他の権限はありません。次のように、名前空間(スキーマ)に対してUSAGEを付与し、テーブルとビューに対してSELECTを個別に付与する必要があります。

GRANT CONNECT ON DATABASE mydb TO xxx;
-- This assumes you're actually connected to mydb..
GRANT USAGE ON SCHEMA public TO xxx;
GRANT SELECT ON mytable TO xxx;

複数のテーブル/ビュー(PostgreSQL 9.0以降)

PostgreSQLの最新バージョンでは、1つずつ入力するのではなく、1つのコマンドを使用してスキーマ内のすべてのテーブル/ビューなどに権限を付与できます。

GRANT SELECT ON ALL TABLES IN SCHEMA public TO xxx;

これは、すでに作成されているテーブルにのみ影響します。さらに強力な方法として、将来、新しいオブジェクトデフォルトの役割を自動的に割り当てることができます。

ALTER DEFAULT PRIVILEGES IN SCHEMA public
   GRANT SELECT ON TABLES TO xxx;

デフォルトでは、これはこのコマンドを発行したユーザーが作成したオブジェクト(テーブル)にのみ影響することに注意してください。ただし、発行ユーザーがメンバーである任意のロールに設定することもできます。ただし、新しいオブジェクトを作成するときに、メンバーになっているすべてのロールのデフォルトの権限を取得するわけではないので、まだ問題があります。データベースに所有ロールがあり、スキーマの変更がその所有ロールとして実行されるというアプローチを採用する場合は、その所有ロールにデフォルトの特権を割り当てる必要があります。私見これはすべてややこしいので、機能的なワークフローを思いつくために実験する必要があるかもしれません。

複数のテーブル/ビュー(9.0より前のバージョンのPostgreSQL)

長時間にわたる複数テーブルの変更でのエラーを回避するには、次の「自動」プロセスを使用して、GRANT SELECT各テーブル/ビューに必要なものを生成することをお勧めします。

SELECT 'GRANT SELECT ON ' || relname || ' TO xxx;'
FROM pg_class JOIN pg_namespace ON pg_namespace.oid = pg_class.relnamespace
WHERE nspname = 'public' AND relkind IN ('r', 'v', 'S');

これにより、コピーアンドペーストができるように、関連するGRANTコマンドがすべてのテーブル、ビュー、シーケンスのGRANT SELECTに出力されます。当然、これはすでに作成されているテーブルにのみ適用されます。


22
PG9に関する編集内容を投稿の上部に配置する必要があります。
Danilo Bargen

5
いいね。追加したいことの1つは、このユーザーがシーケンスを読み取れるようにする必要があることです。so:スキーマのすべてのシーケンスの選択をGRANT SELECT xxxに許可します。
JJC、2015年

26
このユーザーが新しいテーブルを作成できないようにするには、私がしなければならなかったことに注意してくださいREVOKE CREATE ON SCHEMA public FROM PUBLIC;。それがなければ、「読み取り専用」ユーザーは既存のテーブルを変更できませんでしたが、スキーマに新しいテーブルを作成し、それらのテーブルからデータを追加/削除できます。
Ajedi32 2015

3
@ Ajedi32これは受け入れられた回答の一部であるはずです!ありがとう
Asfand Qazi 2016

12
私のような初心者にとって、コンソールを起動する必要があることを言及する価値があると思いpsql mydbます。個人的にそれを理解するにはかなりの時間がかかりました。これが誰かを助けることを願っています。
Anass

41

PostgreSQL 9.0(現在ベータテスト中)はそれを行う簡単な方法があることに注意してください:

test=> GRANT SELECT ON ALL TABLES IN SCHEMA public TO joeuser;

3
これが機能するためには、特定のデータベースにいる必要がありました。Postgresql 9.5。
user1158559 2016

8
これは、スキーマ内の既存のテーブルに対してのみ機能します。書き込みユーザーが後でテーブルを作成または置換した場合、読み取り専用ユーザーはそれらにアクセスできません
16

33

このブログから引用したリファレンス:

読み取り専用ユーザーを作成するスクリプト:

CREATE ROLE Read_Only_User WITH LOGIN PASSWORD 'Test1234' 
NOSUPERUSER INHERIT NOCREATEDB NOCREATEROLE NOREPLICATION VALID UNTIL 'infinity';

この読み取り専用ユーザーに権限を割り当てます:

GRANT CONNECT ON DATABASE YourDatabaseName TO Read_Only_User;
GRANT USAGE ON SCHEMA public TO Read_Only_User;
GRANT SELECT ON ALL TABLES IN SCHEMA public TO Read_Only_User;
GRANT SELECT ON ALL SEQUENCES IN SCHEMA public TO Read_Only_User;

今後作成されるすべての新しいテーブルを読み取る権限を割り当てます

ALTER DEFAULT PRIVILEGES IN SCHEMA public GRANT SELECT ON TABLES TO Read_Only_User;

6
これは、1つの欠けている点を除いて、非常に良い答え ALTER DEFAULT PRIVILEGES IN SCHEMA public GRANT SELECT ON TABLES TO Read_Only_User; です。将来的には、同じDBで作成されたすべてのテーブルを読み取ることもできます。
Ravbaker、

2
読み取り専用ユーザーにシーケンスへのアクセスを許可するのは珍しいことです。シーケンスを読み取るとそれが更新され、通常はにのみ必要ですINSERT
jpmc26

完全を期すため、おそらく追加:GRANT EXECUTE ON ALL FUNCTIONS IN SCHEMA schema_name TO Read_Only_User;
ファビアンHaddadi

@ jpmc26:それはあなたが推奨することを意味しますGRANT ALL ON ALL SEQUENCES IN SCHEMA schema_name TO Read_Only_Userか?
Fabien Haddadi、

@FabienHaddadiこれは、通常の要件を満たさない限り、シーケンスに対する権限を読み取り専用ユーザーに付与する必要がないことを意味します。
jpmc26

24

以下は、読み取り専用ユーザーを追加するために見つけた最良の方法です(PostgreSQL 9.0以降を使用)。

$ sudo -upostgres psql postgres
postgres=# CREATE ROLE readonly WITH LOGIN ENCRYPTED PASSWORD '<USE_A_NICE_STRONG_PASSWORD_PLEASE';
postgres=# GRANT SELECT ON ALL TABLES IN SCHEMA public TO readonly;

次に、関連するすべてのマシン(マスター+読み取りスレーブ/ホットスタンバイなど)にログインし、次のコマンドを実行します。

$ echo "hostssl <PUT_DBNAME_HERE> <PUT_READONLY_USERNAME_HERE> 0.0.0.0/0 md5" | sudo tee -a /etc/postgresql/9.2/main/pg_hba.conf
$ sudo service postgresql reload

2
私はこのアプローチが好きですが、[データベース] [データベース]を[ユーザーまたはロール]に付与する必要もあります。そして、[ユーザーまたはロール]に公開されているスキーマの使用を許可します。
Ian Connor

1
パブリックスキーマでは、このようなユーザーが引き続きテーブルを作成できます。また、新しいテーブルもシーケンスもカバーされていません。残念ながら、これはすべてこれよりもかなり複雑です。:-/私はそれをもう少し検証したら、私がやったことを投稿します。
JJC 2014

上記のスクリプトでは、ロールを2回作成しようとしています。ログイン用のロールを有効にしてパスワードを設定するときに「ALTER ROLE ...」を使用するつもりだったと思います
Bogdan

既にユーザーがいる場合は、読み取り専用の役割を作成し、select permsを付与した後、新しい役割をユーザーに付与します
。GRANT

18

デフォルトでは、新しいユーザーにはテーブルを作成する権限があります。読み取り専用ユーザーの作成を計画している場合、これはおそらく必要なことではありません。

PostgreSQL 9.0以降で真の読み取り専用ユーザーを作成するには、次の手順を実行します。

# This will prevent default users from creating tables
REVOKE CREATE ON SCHEMA public FROM public;

# If you want to grant a write user permission to create tables
# note that superusers will always be able to create tables anyway
GRANT CREATE ON SCHEMA public to writeuser;

# Now create the read-only user
CREATE ROLE readonlyuser WITH LOGIN ENCRYPTED PASSWORD 'strongpassword';
GRANT SELECT ON ALL TABLES IN SCHEMA public TO readonlyuser;

読み取り専用ユーザーにテーブルを一覧表示する権限がない場合(つまり\d、結果を返さない場合)はUSAGE、スキーマに対する権限がないためと考えられます。USAGEユーザーが割り当てられた権限を実際に使用できるようにする権限です。これの意味は何ですか?よく分かりません。修正するには:

# You can either grant USAGE to everyone
GRANT USAGE ON SCHEMA public TO public;

# Or grant it just to your read only user
GRANT USAGE ON SCHEMA public TO readonlyuser;

8

そのための便利なスクリプトを作成しました。pg_grant_read_to_db.sh。このスクリプトは、データベーススキーマのすべてのテーブル、ビュー、シーケンスの指定されたロールに読み取り専用権限を付与し、それらをデフォルトとして設定します。


4

許可する前にデータベースに接続することを忘れない限り、考えられるすべての解決策を読んでいますが、他のすべての解決策に感謝します!!!

user@server:~$ sudo su - postgres

psqlユーザーを作成します。

postgres@server:~$ createuser --interactive 
Enter name of role to add: readonly
Shall the new role be a superuser? (y/n) n
Shall the new role be allowed to create databases? (y/n) n
Shall the new role be allowed to create more new roles? (y/n) n

psql cliを起動し、作成したユーザーのパスワードを設定します。

postgres@server:~$ psql
psql (10.6 (Ubuntu 10.6-0ubuntu0.18.04.1), server 9.5.14)
Type "help" for help.

postgres=# alter user readonly with password 'readonly';
ALTER ROLE

ターゲットデータベースに接続します。

postgres=# \c target_database 
psql (10.6 (Ubuntu 10.6-0ubuntu0.18.04.1), server 9.5.14)
You are now connected to database "target_database" as user "postgres".

必要なすべての特権を付与します。

target_database=# GRANT CONNECT ON DATABASE target_database TO readonly;
GRANT

target_database=# GRANT USAGE ON SCHEMA public TO readonly ;
GRANT

target_database=# GRANT SELECT ON ALL TABLES IN SCHEMA public TO readonly ;
GRANT

ターゲットdb public shemaのデフォルト特権を変更します。

target_database=# ALTER DEFAULT PRIVILEGES IN SCHEMA public GRANT SELECT ON TABLES TO readonly;
ALTER DEFAULT PRIVILEGES

3

データベースがパブリックスキーマにある場合、それは簡単です(これは、すでにを作成済みであることを前提としていますreadonlyuser

db=> GRANT SELECT ON ALL TABLES IN SCHEMA public to readonlyuser;
GRANT
db=> GRANT CONNECT ON DATABASE mydatabase to readonlyuser;
GRANT
db=> GRANT SELECT ON ALL SEQUENCES IN SCHEMA public to readonlyuser;
GRANT

データベースでを使用している場合はcustomschema、上記を実行しますが、コマンドを1つ追加します。

db=> ALTER USER readonlyuser SET search_path=customschema, public;
ALTER ROLE

1

これを行う簡単な方法は、データベースの各テーブルで選択を許可することです。

postgres=# grant select on db_name.table_name to read_only_user;

データベースのメタデータからグラントステートメントを生成することで、自動化できます。



0

despeszのリンクに応じて投稿されたリンクから取得

Postgres 9.xには、要求された処理を実行する機能があるようです。以下のデータベースオブジェクトの付与に関する段落を参照してください。

http://www.postgresql.org/docs/current/interactive/sql-grant.html

「1つ以上のスキーマ内の同じタイプのすべてのオブジェクトに権限を付与するオプションもあります。この機能は現在、テーブル、シーケンス、および関数に対してのみサポートされています(ただし、すべてのテーブルにはビューが含まれると見なされることに注意してください。および外部テーブル)。」

このページでは、ROLEと「ALL PRIVILEGES」と呼ばれるPRIVILEGEの使用についても説明します。

また、SQLの標準と比較したGRANT機能の情報も含まれています。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.