sql >> Base de Datos >  >> RDS >> PostgreSQL

PostgreSQL:al usuario de la base de datos solo se le debe permitir llamar a funciones

No hay "privilegio en SELECT ". Todo lo que necesita es el privilegio de EXECUTE funciones La función relevante se puede ejecutar con SECURITY DEFINER heredar todos los privilegios del propietario. Para restringir la posible escalada de privilegios a un mínimo a priori, haga que un rol de daemon posea funciones relevantes con solo los privilegios necesarios, ¡no un superusuario!

Receta

Como superusuario...

Cree un rol que no sea superusuario myuser .

CREATE ROLE myuser PASSWORD ...;

Crear un rol de grupo mygroup y hacer myuser miembro en él.

CREATE ROLE mygroup;
GRANT mygroup TO myuser;

Es posible que desee agregar más usuarios como myuser más tarde.

No conceder ningún privilegio a myuser .
Solo concédelos a mygroup :

  • GRANT CONNECT ON DATABASE mydb TO mygroup;
  • GRANT USAGE ON SCHEMA public TO mygroup;
  • GRANT EXECUTE ON FUNCTION foo() TO mygroup;

Quitar todo privilegios para public que myuser no debería haberlo hecho.

REVOKE ALL ON ALL TABLES IN SCHEMA myschema FROM public;

Puede haber más. Cito el manual:

Crear un rol de demonio poseer funciones relevantes.

CREATE ROLE mydaemon;

Otorgue solo los privilegios necesarios para ejecutar estas funciones a mydaemon , (incluyendo EXECUTE ON FUNCTION para permitir que se llame a otra función). Nuevamente, puede usar roles de grupo para agrupar privilegios y otorgarlos a mydaemon

GRANT bundle1 TO mydaemon;

Además, puede usar DEFAULT PRIVILEGES para otorgar automáticamente ciertos privilegios para objetos futuros a un paquete o al daemon directamente:

ALTER DEFAULT PRIVILEGES IN SCHEMA myschema GRANT SELECT ON TABLES    TO bundle1;
ALTER DEFAULT PRIVILEGES IN SCHEMA myschema GRANT USAGE  ON SEQUENCES TO bundle1;

Esto se aplica solo al rol para el que se ejecuta. Según la documentación:

Para cubrir también objetos preexistentes en el esquema (consulte comentario de Rob ):

GRANT SELECT ON ALL TABLES    IN SCHEMA public TO bundle1;
GRANT USAGE  ON ALL SEQUENCES IN SCHEMA public TO bundle1;

Hacer mydaemon propias funciones relevantes. Podría verse así:

CREATE OR REPLACE FUNCTION foo()
  ...
SECURITY DEFINER SET search_path = myschema, pg_temp;

ALTER FUNCTION foo() OWNER TO mydaemon;
REVOKE EXECUTE ON FUNCTION foo() FROM public;
GRANT  EXECUTE ON FUNCTION foo() TO mydaemon;
GRANT  EXECUTE ON FUNCTION foo() TO mygroup;
-- possibly others ..

###Nota
Debido a este error en la versión actual 1.16.1 de pgAdmin el comando necesario

REVOKE EXECUTE ON FUNCTION foo() FROM public;

falta en el script DDL de ingeniería inversa. Recuerde agregarlo cuando vuelva a crear.
Este error se solucionó en la versión actual pgAdmin 1.18.1.