PostgreSQL에 대한 Amazon RDS 위임 확장 지원 사용 - Amazon Relational Database Service

PostgreSQL에 대한 Amazon RDS 위임 확장 지원 사용

PostgreSQL에 대한 Amazon RDS 위임 확장 지원을 사용하면 rds_superuser 역할이 아닌 사용자에게도 확장 관리를 위임할 수 있습니다. 이 위임 확장 지원을 통해 rds_extension이라는 새 역할이 생성되며, 이 역할이 할당되어야 해당 사용자가 다른 확장을 관리할 수 있습니다. 이 역할은 확장을 생성하고, 업데이트하고, 삭제할 수 있습니다.

RDS DB 인스턴스에 설치할 수 있는 확장을 rds.allowed_extensions 파라미터에 등록하여 지정할 수 있습니다. 자세한 내용은 Amazon RDS for PostgreSQL로 PostgreSQL 확장 사용을 참조하세요.

rds.allowed_delegated_extensions 파라미터를 사용하여 rds_extension 역할이 있는 사용자가 관리할 수 있는 가용 확장 목록을 제한할 수 있습니다.

위임 확장 지원은 다음 버전에서 사용할 수 있습니다.

  • 모든 상위 버전

  • 16.4 이상의 16 버전

  • 15.8 이상의 15 버전

  • 14.13 이상의 14 버전

  • 13.16 이상의 13 버전

  • 12.20 이상의 12 버전

사용자에게 위임 확장 지원 활성화

사용자에게 위임 확장 지원을 활성화하려면 다음을 수행해야 합니다.

  1. 사용자에게 rds_extension 역할 부여 - rds_superuser 권한으로 데이터베이스에 연결하고 다음 명령을 실행합니다.

    Postgres => grant rds_extension to user_name;
  2. 위임된 사용자가 관리할 수 있는 확장 목록 설정 - rds.allowed_delegated_extensions를 통해 DB 클러스터 파라미터에서 rds.allowed_extensions를 사용하여 가용 확장의 하위 집합을 지정할 수 있습니다. 다음 수준 중 하나에서 이 작업을 수행할 수 있습니다.

    • 클러스터 또는 인스턴스 파라미터 그룹에서 AWS Management Console 또는 API를 통해 가능합니다. 자세한 내용은 Amazon RDS의 파라미터 그룹 단원을 참조하십시오.

    • 데이터베이스 수준에서 다음 명령을 사용하세요.

      alter database database_name set rds.allowed_delegated_extensions = 'extension_name_1, extension_name_2,...extension_name_n';
    • 사용자 수준에서 다음 명령을 사용하세요.

      alter user user_name set rds.allowed_delegated_extensions = 'extension_name_1, extension_name_2,...extension_name_n';
    참고

    rds.allowed_delegated_extensions 동적 파라미터를 변경한 후에는 데이터베이스를 다시 시작할 필요가 없습니다.

  3. 확장 생성 프로세스 중에 생성된 객체에 대한 위임된 사용자 액세스 허용 - 특정 확장에서는 추가 권한을 부여해야 rds_extension 역할을 가진 사용자가 해당 개체에 액세스할 수 있는 개체를 만들 수 있습니다. rds_superuser는 위임된 사용자에게 해당 객체에 대한 액세스 권한을 부여해야 합니다. 이벤트 트리거를 사용하여 위임된 사용자에게 권한을 자동으로 부여하는 것도 한 가지 방법입니다. 자세한 정보는 위임 확장에 대한 지원 비활성화에서 이벤트 트리거 예제를 참조하세요.

RDS 위임 확장 지원에서 PostgreSQL에 대해 사용되는 구성

구성 이름 설명 기본 값 참고 권한을 수정하거나 부여할 수 있는 사람

rds.allowed_delegated_extensions

이 파라미터는 rds_extension 역할이 데이터베이스에서 관리할 수 있는 확장을 제한합니다. rds.allowed_extensions의 하위 집합이어야 합니다.

빈 문자열

  • 기본적으로 이 파라미터는 빈 문자열이므로 rds_extension을 사용하는 사용자에게 확장이 위임되지 않았음을 의미합니다.

  • 사용자에게 권한이 있는 경우 모든 지원되는 확장을 추가할 수 있습니다. 이렇게 하려면 rds.allowed_delegated_extensions 파라미터를 쉼표로 구분된 확장 이름(문자열)으로 설정합니다. 이 파라미터에 확장 목록을 추가하면 rds_extension 역할의 사용자가 설치할 수 있는 확장을 명시적으로 파악할 수 있습니다.

  • *로 설정하면 rds_allowed_extensions에 나열된 모든 확장이 rds_extension 역할의 사용자에게 위임된다는 의미입니다.

이 파라미터 설정에 대한 자세한 내용은 사용자에게 위임 확장 지원 활성화 섹션을 참조하세요.

rds_superuser

rds.allowed_extensions

이 파라미터를 사용하면 고객이 RDS DB 인스턴스에 설치할 수 있는 확장을 제한할 수 있습니다. 자세한 내용은 PostgreSQL 확장 설치 제한을 참조하세요.

"*"

기본적으로 이 파라미터는 ‘*’로 설정되어 있습니다. 즉, RDS for PostgreSQL과 Aurora PostgreSQL에서 지원되는 모든 확장은 필요한 권한이 있는 사용자가 만들 수 있습니다.

이 값이 비어 있으면 RDS DB 인스턴스에 확장을 설치할 수 없습니다.

관리자

rds-delegated_extension_allow_drop_cascade

이 파라미터는 rds_extension 권한이 있는 사용자가 캐스케이드 옵션을 사용하여 확장을 삭제할 수 있는 기능을 제어합니다.

기본적으로 rds-delegated_extension_allow_drop_cascadeoff로 설정됩니다. 즉, rds_extension 사용자는 캐스케이드 옵션을 사용하여 확장 프로그램을 삭제할 수 없습니다.

이 기능을 부여하려면 rds.delegated_extension_allow_drop_cascade 파라미터를 on으로 설정해야 합니다.

rds_superuser

위임 확장에 대한 지원 비활성화

부분적으로 비활성화

위임된 사용자는 새 확장을 만들 수는 없지만 기존 확장을 계속 업데이트할 수는 있습니다.

  • DB 클러스터 파라미터 그룹에서 rds.allowed_delegated_extensions를 기본값으로 재설정합니다.

  • 데이터베이스 수준에서 다음 명령을 사용하세요.

    alter database database_name reset rds.allowed_delegated_extensions;
  • 사용자 수준에서 다음 명령을 사용하세요.

    alter user user_name reset rds.allowed_delegated_extensions;
전체적으로 비활성화

사용자로부터 rds_extension 역할을 취소하면 사용자는 표준 권한으로 되돌아갑니다. 해당 사용자는 더 이상 확장을 생성, 업데이트 또는 삭제할 수 없습니다.

postgres => revoke rds_extension from user_name;
이벤트 트리거 예제

확장 생성 시 만들어진 객체에 대한 권한 설정이 필요한 확장을 rds_extension 권한이 있는 위임된 사용자가 사용할 수 있도록 하려면, 아래 이벤트 트리거 예제를 사용자 지정하고 위임된 사용자가 전체 기능에 액세스할 수 있도록 하려는 확장만 추가하면 됩니다. 이 이벤트 트리거는 template1(기본 템플릿)에서 만들 수 있으므로, template1에서 만든 모든 데이터베이스에는 해당 이벤트 트리거가 있습니다. 위임된 사용자가 확장을 설치하면 이 트리거는 확장에서 생성된 객체에 대한 소유권을 자동으로 부여합니다.

CREATE OR REPLACE FUNCTION create_ext() RETURNS event_trigger AS $$ DECLARE schemaname TEXT; databaseowner TEXT; r RECORD; BEGIN IF tg_tag = 'CREATE EXTENSION' and current_user != 'rds_superuser' THEN RAISE NOTICE 'SECURITY INVOKER'; RAISE NOTICE 'user: %', current_user; FOR r IN SELECT * FROM pg_event_trigger_ddl_commands() LOOP CONTINUE WHEN r.command_tag != 'CREATE EXTENSION' OR r.object_type != 'extension'; schemaname = ( SELECT n.nspname FROM pg_catalog.pg_extension AS e INNER JOIN pg_catalog.pg_namespace AS n ON e.extnamespace = n.oid WHERE e.oid = r.objid ); databaseowner = ( SELECT pg_catalog.pg_get_userbyid(d.datdba) FROM pg_catalog.pg_database d WHERE d.datname = current_database() ); RAISE NOTICE 'Record for event trigger %, objid: %,tag: %, current_user: %, schema: %, database_owenr: %', r.object_identity, r.objid, tg_tag, current_user, schemaname, databaseowner; IF r.object_identity = 'address_standardizer_data_us' THEN EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.us_gaz TO %I WITH GRANT OPTION;', schemaname, databaseowner); EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.us_lex TO %I WITH GRANT OPTION;', schemaname, databaseowner); EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.us_rules TO %I WITH GRANT OPTION;', schemaname, databaseowner); ELSIF r.object_identity = 'dict_int' THEN EXECUTE format('ALTER TEXT SEARCH DICTIONARY %I.intdict OWNER TO %I;', schemaname, databaseowner); ELSIF r.object_identity = 'pg_partman' THEN EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.part_config TO %I WITH GRANT OPTION;', schemaname, databaseowner); EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.part_config_sub TO %I WITH GRANT OPTION;', schemaname, databaseowner); EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON TABLE %I.custom_time_partitions TO %I WITH GRANT OPTION;', schemaname, databaseowner); ELSIF r.object_identity = 'postgis_topology' THEN EXECUTE format('GRANT SELECT, UPDATE, INSERT, DELETE ON ALL TABLES IN SCHEMA topology TO %I WITH GRANT OPTION;', databaseowner); EXECUTE format('GRANT USAGE, SELECT ON ALL SEQUENCES IN SCHEMA topology TO %I WITH GRANT OPTION;', databaseowner); EXECUTE format('GRANT EXECUTE ON ALL FUNCTIONS IN SCHEMA topology TO %I WITH GRANT OPTION;', databaseowner); EXECUTE format('GRANT USAGE ON SCHEMA topology TO %I WITH GRANT OPTION;', databaseowner); END IF; END LOOP; END IF; END; $$ LANGUAGE plpgsql SECURITY DEFINER; CREATE EVENT TRIGGER log_create_ext ON ddl_command_end EXECUTE PROCEDURE create_ext();

Amazon RDS 위임 확장 지원 사용의 이점

PostgreSQL에 대한 Amazon RDS 위임 확장 지원을 사용하면 rds_superuser 역할이 아닌 사용자에게도 확장 관리를 안전하게 위임할 수 있습니다. 이 기능에는 다음과 같은 이점이 있습니다.

  • 원하는 사용자에게 확장 관리를 쉽게 위임할 수 있습니다.

  • 이 작업에는 rds_superuser 역할이 필요하지 않습니다.

  • 동일한 DB 클러스터의 여러 데이터베이스에 대해 서로 다른 확장 세트를 지원하는 기능을 제공합니다.

PostgreSQL에 대한 Amazon RDS 위임 확장 지원 제한

  • 확장 생성 프로세스 중에 생성되는 객체에서 확장이 제대로 작동하려면 추가 권한이 필요할 수 있습니다.

  • log_fdw, pg_cron, pg_tle, pgactive, pglogical, postgis_raster, postgis_tiger_geocoder, postgis_topology를 포함한 일부 확장은 위임된 확장 사용자가 기본적으로 관리할 수 없습니다.

특정 확장에 필요한 권한

다음과 같은 확장을 생성, 사용 또는 업데이트하려면 위임된 사용자에게 다음과 같은 함수, 테이블 및 스키마에 대해 필요한 권한이 있어야 합니다.

소유권이나 권한이 필요한 확장 함수 스키마 텍스트 검색 사전 설명

address_standardizer_data_us

없음

us_gaz, us_lex, us_lex, I.us_rules

없음

없음

없음

amcheck

bt_index_check, bt_index_parent_check

없음

없음

없음

없음

dict_int

없음

없음

없음

intdict

없음

pg_partman

없음

custom_time_partitions, part_config, part_config_sub

없음

없음

없음

pg_stat_statements

없음

없음

없음

없음

없음

PostGIS

st_tileenvelope

spatial_ref_sys

없음

없음

없음

postgis_raster

없음

없음

없음

없음

없음

postgis_topology

없음

topology, layer

topology

없음

위임된 사용자는 데이터베이스 소유자여야 함

log_fdw

create_foreign_table_for_log_file

없음

없음

없음

없음

rds_tools

role_password_encryption_type

없음

없음

없음

없음

postgis_tiger_geocoder

없음

geocode_settings_default, geocode_settings

tiger

없음

없음

pg_freespacemap

pg_freespace

없음

없음

없음

없음

pg_visibility

pg_visibility

없음

없음

없음

없음

보안 고려 사항

rds_extension 역할이 있는 사용자는 접속 권한이 있는 모든 데이터베이스의 확장을 관리할 수 있다는 점을 기억하세요. 위임된 사용자가 단일 데이터베이스의 확장을 관리하도록 하려는 경우, 각 데이터베이스의 모든 공개 권한을 취소한 다음 해당 특정 데이터베이스의 연결 권한을 위임 사용자에게 명시적으로 부여하는 것이 좋습니다.

사용자가 여러 데이터베이스의 정보에 액세스할 수 있도록 하는 확장에는 여러 가지가 있습니다. 이러한 확장을 rds.allowed_delegated_extensions에 추가하기 전에 rds_extension 권한을 부여한 사용자가 데이터베이스 간 기능을 사용할 수 있는지 확인하세요. 예를 들어, postgres_fdwdblink는 동일한 인스턴스 또는 원격 인스턴스의 여러 데이터베이스를 쿼리할 수 있는 기능을 제공합니다. log_fdw는 인스턴스의 모든 데이터베이스에 대한 postgres 엔진 로그 파일을 읽습니다. 이 로그 파일에는 여러 데이터베이스의 느린 쿼리나 오류 메시지가 포함될 수 있습니다. pg_cron은 예약된 백그라운드 작업을 DB 인스턴스에서 실행할 수 있도록 하고 작업이 다른 데이터베이스에서 실행되도록 구성할 수 있습니다.

확장 삭제 캐스케이드 비활성화

rds_extension 역할의 사용자가 캐스케이드 옵션을 사용하여 확장을 삭제하는 기능은 rds.delegated_extension_allow_drop_cascade 파라미터에 의해 제어됩니다. 기본적으로 rds-delegated_extension_allow_drop_cascadeoff로 설정됩니다. 즉, rds_extension 역할의 사용자는 아래 쿼리에 나와 있는 캐스케이드 옵션으로 확장을 삭제할 수 없습니다.

DROP EXTENSION CASCADE;

이렇게 하면 확장에 종속된 객체와 해당 객체에 종속된 모든 객체가 자동으로 삭제되기 때문입니다. 캐스케이드 옵션을 사용하려고 시도하면 오류가 발생합니다.

이 기능을 부여하려면 rds.delegated_extension_allow_drop_cascade 파라미터를 on으로 설정해야 합니다.

rds.delegated_extension_allow_drop_cascade 동적 파라미터를 변경하기 위해 데이터베이스를 다시 시작할 필요가 없습니다. 다음 수준 중 하나에서 이 작업을 수행할 수 있습니다.

  • 클러스터 또는 인스턴스 파라미터 그룹에서 AWS Management Console 또는 API를 통해 가능합니다.

  • 데이터베이스 수준에서 다음 명령을 사용하세요.

    alter database database_name set rds.delegated_extension_allow_drop_cascade = 'on';
  • 사용자 수준에서 다음 명령을 사용하세요.

    alter role tenant_user set rds.delegated_extension_allow_drop_cascade = 'on';

위임 확장 지원을 사용하여 추가할 수 있는 확장의 예

  • rds_tools

    extension_test_db=> create extension rds_tools; CREATE EXTENSION extension_test_db=> SELECT * from rds_tools.role_password_encryption_type() where rolname = 'pg_read_server_files'; ERROR: permission denied for function role_password_encryption_type
  • amcheck

    extension_test_db=> CREATE TABLE amcheck_test (id int); CREATE TABLE extension_test_db=> INSERT INTO amcheck_test VALUES (generate_series(1,100000)); INSERT 0 100000 extension_test_db=> CREATE INDEX amcheck_test_btree_idx ON amcheck_test USING btree (id); CREATE INDEX extension_test_db=> create extension amcheck; CREATE EXTENSION extension_test_db=> SELECT bt_index_check('amcheck_test_btree_idx'::regclass); ERROR: permission denied for function bt_index_check extension_test_db=> SELECT bt_index_parent_check('amcheck_test_btree_idx'::regclass); ERROR: permission denied for function bt_index_parent_check
  • pg_freespacemap

    extension_test_db=> create extension pg_freespacemap; CREATE EXTENSION extension_test_db=> SELECT * FROM pg_freespace('pg_authid'); ERROR: permission denied for function pg_freespace extension_test_db=> SELECT * FROM pg_freespace('pg_authid',0); ERROR: permission denied for function pg_freespace
  • pg_visibility

    extension_test_db=> create extension pg_visibility; CREATE EXTENSION extension_test_db=> select * from pg_visibility('pg_database'::regclass); ERROR: permission denied for function pg_visibility
  • postgres_fdw

    extension_test_db=> create extension postgres_fdw; CREATE EXTENSION extension_test_db=> create server myserver foreign data wrapper postgres_fdw options (host 'foo', dbname 'foodb', port '5432'); ERROR: permission denied for foreign-data wrapper postgres_fdw