PostgreSQL
 sql >> Database >  >> RDS >> PostgreSQL

Rilascia un ruolo con privilegi

Esegui questo in ogni database dello stesso cluster in cui il ruolo potrebbe possedere qualsiasi cosa o disporre di privilegi concessi:

REASSIGN OWNED BY some_role_name TO postgres;
DROP OWNED BY some_role_name;

postgres essendo il superutente predefinito, puoi sceglierne un altro. Possiederà oggetti attualmente di proprietà del vecchio ruolo. Immediatamente dopo REASSIGN OWNED , non sono rimasti oggetti di proprietà dallo stesso utente. Può sembrare poco intuitivo eseguire DROP OWNED . La formulazione del comando è fuorviante, poiché anche revoca tutti i privilegi e i privilegi predefiniti per il ruolo nello stesso database. Il manuale:

Il grassetto è mio.
Devi ancora eseguirlo in ogni singolo database dove il ruolo possiede qualcosa o dispone di privilegi concessi. Il manuale:

Infine, esegui (una volta):

DROP role some_role_name;

I ruoli sono archiviati in un catalogo di sistema a livello di cluster, mentre la proprietà e i privilegi sugli oggetti sono archiviati in cataloghi di sistema locali del database.

Spiegazione dettagliata in questa risposta correlata:

C'è una pagina correlata nel manuale con le istruzioni .

Automazione completa

Non esiste un unico comando per fare tutto. Ma puoi lasciare che Postgres generi uno script psql completo per te.

Le dipendenze per i ruoli sono archiviate nel catalogo di sistema pg_shdepend :

Dal momento che abbiamo (potenzialmente) bisogno di connetterci a database diversi, abbiamo bisogno di una combinazione di meta-comandi psql (\c my_database ) e comandi SQL DDL come mostrato sopra. Crea questa funzione da qualche parte nel tuo cluster di database una volta:

CREATE OR REPLACE FUNCTION f_generate_ddl_to_remove_role(dead_role_walking regrole)
  RETURNS text
  LANGUAGE sql AS
$func$
SELECT concat_ws(
   E'\n'
 ,(SELECT string_agg(format(E'\\c %I\nREASSIGN OWNED BY %2$s TO postgres; DROP OWNED BY %2$s;'
                          , d.datname, dead_role_walking)
                   , E'\n')
   FROM  (
      SELECT DISTINCT dbid
      FROM   pg_shdepend
      WHERE  refobjid = dead_role_walking
      ) s
   JOIN   pg_database d ON d.oid = s.dbid)
 , format(E'DROP role %s;\n', dead_role_walking)
   )
$func$;

Chiama:

SELECT f_generate_ddl_to_remove_role('some_role_name');

Produce una stringa come:

\c my_db1
REASSIGN OWNED BY some_role_name TO postgres; DROP OWNED BY some_role_name;
\c my_db2
REASSIGN OWNED BY some_role_name TO postgres; DROP OWNED BY some_role_name;
DROP role some_role_name;

Oppure, se il ruolo non possiede nulla e non ha privilegi, basta:

DROP role some_role_name;

Se fornisci un nome di ruolo inesistente, viene visualizzato un errore.

Copia la stringa (senza racchiudere virgolette singole) in una sessione psql aperta con un superutente come postgres . Oppure concatena uno script bash con esso. Tutto fatto.

Esistono diverse risposte correlate con ulteriori spiegazioni per SQL dinamico: