2011-12-17 7 views
70

createuser consente la creazione di un utente (ROLE) in PostgreSQL. C'è un modo semplice per verificare se quell'utente (nome) esiste già? torna Altrimenti createuser con un errore:Come verificare se esiste un utente postgres?

createuser: creation of new role failed: ERROR: role "USR_NAME" already exists 

UPDATE: La soluzione deve essere eseguibile da shell preferibilmente, in modo che sia più semplice per automatizzare all'interno di uno script.

risposta

121
SELECT 1 FROM pg_roles WHERE rolname='USR_NAME' 

E in termini di linea di comando (grazie a Erwin):

psql postgres -tAc "SELECT 1 FROM pg_roles WHERE rolname='USR_NAME'" 

rendimenti 1 se trovato e nient'altro.

Cioè:

psql postgres -tAc "SELECT 1 FROM pg_roles WHERE rolname='USR_NAME'" | grep -q 1 || createuser ... 
+0

Ti ricordi qual è la SQL incorporato utilità della riga di comando da eseguire? Alla fine preferirei eseguire e recuperare il risultato dalla shell se possibile. – m33lky

+1

'psql' è il comando. Ma se stai parlando di utility di riga di comando 'createuser' (ovviamente, non ho notato la mancanza di spazio in' create user' all'inizio), quindi potrebbe essere più semplice ignorare lo stato di uscita e reindirizzare l'output a '/ dev/null'. –

+2

@ m33lky: Oppure puoi testare il valore di ritorno di questo comando nella shell (come utente postgres): 'psql postgres -tAc" SELEZIONA 1 DA pg_roles WHERE rolname = 'USR_NAME' "'. Rende '1' se trovato e nient'altro. –

3

Seguendo la stessa idea che a check if a db exists

psql -t -c '\du' | cut -d \| -f 1 | grep -qw <user_to_check> 

e si può utilizzare in uno script come questo:

if psql -t -c '\du' | cut -d \| -f 1 | grep -qw <user_to_check>; then 
    # user exists 
    # $? is 0 
else 
    # ruh-roh 
    # $? is 1 
fi 
+0

Ciò genererebbe un risultato di query più grande della risposta http://stackoverflow.com/a/8546783/107158. Tuttavia, a differenza di quella risposta, questa sarebbe sopravvissuta a una rinomina nella tabella di sistema 'pg_roles', ma non una modifica al comando' \ du'. Quale è più probabile che non cambi? –

2

Spero che questo aiuta coloro di voi che potrebbero farlo in python.
Ho creato uno script/soluzione di lavoro completo su GitHubGist - vedi l'URL sotto questo snippet di codice.

# ref: https://stackoverflow.com/questions/8546759/how-to-check-if-a-postgres-user-exists 
check_user_cmd = ("SELECT 1 FROM pg_roles WHERE rolname='%s'" % (deis_app_user)) 

# our create role/user command and vars 
create_user_cmd = ("CREATE ROLE %s WITH LOGIN CREATEDB PASSWORD '%s'" % (deis_app_user, deis_app_passwd)) 

# ref: https://stackoverflow.com/questions/37488175/simplify-database-psycopg2-usage-by-creating-a-module 
class RdsCreds(): 
    def __init__(self): 
     self.conn = psycopg2.connect("dbname=%s user=%s host=%s password=%s" % (admin_db_name, admin_db_user, db_host, admin_db_pass)) 
     self.conn.set_isolation_level(0) 
     self.cur = self.conn.cursor() 

    def query(self, query): 
     self.cur.execute(query) 
     return self.cur.rowcount > 0 

    def close(self): 
     self.cur.close() 
     self.conn.close() 

db = RdsCreds() 
user_exists = db.query(check_user_cmd) 

# PostgreSQL currently has no 'create role if not exists' 
# So, we only want to create the role/user if not exists 
if (user_exists) is True: 
    print("%s user_exists: %s" % (deis_app_user, user_exists)) 
    print("Idempotent: No credential modifications required. Exiting...") 
    db.close() 
else: 
    print("%s user_exists: %s" % (deis_app_user, user_exists)) 
    print("Creating %s user now" % (deis_app_user)) 
    db.query(create_user_cmd) 
    user_exists = db.query(check_user_cmd) 
    db.close() 
    print("%s user_exists: %s" % (deis_app_user, user_exists)) 

Provides idempotent remote (RDS) PostgreSQL create role/user from python without CM modules, etc.