はじめに
RDSにてPostgreSQLを使っているとき、マスターユーザーとは別のユーザーを作ってそのユーザがオーナーのデータベースを作ろうとするとERROR: must be member of role "xxxxx"
というメッセージが出ることがあります。例を以下に記します。
postgres=> CREATE ROLE testuser001 WITH PASSWORD 'hogehogehoge' LOGIN; CREATE ROLE postgres=> CREATE DATABASE mytestdb001 WITH OWNER testuser001; ERROR: must be member of role "testuser001" postgres=>
この状態の原因と対策を以下に記します。
原因
RDSのマスターユーザー(ここではpostgres
)にSuperuserが付与されていないのが原因です。\du
にて権限を見てみます。
postgres=> \du List of roles Role name | Attributes | Member of -----------------+------------------------------------------------------------+-------------------------------------------------------------------------------------------------------- ------ postgres | Create role, Create DB +| {rds_superuser} | Password valid until infinity | rds_ad | Cannot login | {} rds_iam | Cannot login | {} rds_password | Cannot login | {} rds_replication | Cannot login | {} rds_superuser | Cannot login | {pg_read_all_data,pg_write_all_data,pg_monitor,pg_signal_backend,pg_checkpoint,rds_replication,rds_pass word} rdsadmin | Superuser, Create role, Create DB, Replication, Bypass RLS+| {} | Password valid until infinity | rdsrepladmin | No inheritance, Cannot login, Replication | {} rdstopmgr | | {pg_monitor,pg_checkpoint} postgres=>
このようにマスターユーザー(postgres
)にはSuperuserが付与されておらず、RDS固有のロールであるrdsadmin
にSuperuserが付与されています。
対策
マスターユーザー(postgres
)が新たに作成したユーザー(testuser001
)のメンバにしてあげればOKです。
postgres=> GRANT testuser001 TO postgres; GRANT ROLE postgres=>
これで、当初の目的であるマスターユーザーとは別のユーザーを作ってそのユーザがオーナーのデータベースを作ることができます。
postgres=> CREATE DATABASE mytestdb001 WITH OWNER testuser001; CREATE DATABASE postgres=>
\l
にて確認してみます。
postgres=> \l List of databases Name | Owner | Encoding | Collate | Ctype | ICU Locale | Locale Provider | Access privileges -------------+-------------+----------+-------------+-------------+------------+-----------------+----------------------- mytestdb001 | testuser001 | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | libc | postgres | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | libc | rdsadmin | rdsadmin | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | libc | rdsadmin=CTc/rdsadmin+ | | | | | | | rdstopmgr=Tc/rdsadmin template0 | rdsadmin | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | libc | =c/rdsadmin + | | | | | | | rdsadmin=CTc/rdsadmin template1 | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | libc | =c/postgres + | | | | | | | postgres=CTc/postgres (6 rows) postgres=>
オンプレミスのPostgreSQLですとこのようなことはなかった気がしますので、念の為記録しておきます。
考察
上記ではrdsadmin
の詳細についてスルーしましたが、詳細はAWSの以下のドキュメントに記されています。
オンプレミスのPostgreSQLと同じノリで操作するとこういうところでつまづくので、上記のようなドキュメントには目を通しておいた方が良いかなと考えています。
参考
この記事を書くためにAWS re:Postを検索すると以下の記事がヒットしました。
むやみに権限を付与しなくてもよいかなと思いますが、対策の一つとしてよいかなと考えています。