Смена роли после подключения к базе данных - PullRequest
50 голосов
/ 08 июня 2010

Можно ли изменить роль postgresql, которую использует пользователь при взаимодействии с postgres после первоначального подключения?

База данных будет использоваться в веб-приложении, и я хотел бы использовать правила уровня базы данных для таблиц и схем с пулами соединений. Из прочтения документации postgresql выясняется, что я могу поменяться ролями, если первоначально подключаюсь как пользователь с ролью суперпользователя, но я бы предпочел изначально подключиться как пользователь с минимальными разрешениями и переключаться по мере необходимости. Было бы хорошо указать пароль пользователя при переключении (на самом деле я бы предпочел его).

Чего мне не хватает?

Обновление : я пробовал и SET ROLE, и SET SESSION AUTHORIZATION, как предложено @Milen, однако ни одна из команд не работает, если пользователь не является суперпользователем:

$ psql -U test
psql (8.4.4)
Type "help" for help.

test=> \du test
          List of roles
 Role name | Attributes |   Member of    
-----------+------------+----------------
 test      |            | {connect_only}

test=> \du test2
          List of roles
 Role name | Attributes |   Member of    
-----------+------------+----------------
 test2     |            | {connect_only}

test=> set role test2;
ERROR:  permission denied to set role "test2"
test=> \q

Ответы [ 3 ]

38 голосов
/ 26 октября 2013
--create a user that you want to use the database as:

create role neil;

--create the user for the web server to connect as:

create role webgui noinherit login password 's3cr3t';

--let webgui set role to neil:

grant neil to webgui; --this looks backwards but is correct.

webgui теперь входит в группу neil, поэтому webgui может звонить set role neil. Однако webgui не наследовал разрешения neil.

Позже, войдите как webgui:

psql -d some_database -U webgui
(enter s3cr3t as password)

set role neil;

webgui для этого не требуется разрешение superuser.

Вы хотите set role в начале сеанса базы данных и сбросить его в конце сеанса. В веб-приложении это соответствует получению соединения из пула соединений с базой данных и его освобождению соответственно. Вот пример использования пула соединений Tomcat и Spring Security:

public class SetRoleJdbcInterceptor extends JdbcInterceptor {

    @Override
    public void reset(ConnectionPool connectionPool, PooledConnection pooledConnection) {

        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();

        if(authentication != null) {
            try {

                /* 
                  use OWASP's ESAPI to encode the username to avoid SQL Injection. Can't use parameters with SET ROLE. Need to write PG codec.

                  Or use a whitelist-map approach
                */
                String username = ESAPI.encoder().encodeForSQL(MY_CODEC, authentication.getName());

                Statement statement = pooledConnection.getConnection().createStatement();
                statement.execute("set role \"" + username + "\"");
                statement.close();
            } catch(SQLException exp){
                throw new RuntimeException(exp);
            }
        }
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {

        if("close".equals(method.getName())){
            Statement statement = ((Connection)proxy).createStatement();
            statement.execute("reset role");
            statement.close();
        }

        return super.invoke(proxy, method, args);
    }
}
12 голосов
/ 08 июня 2010
0 голосов
/ 12 декабря 2018

Если кому-то это все еще нужно (как и мне).

Указанное имя_роли должно быть ролью, членом которой является текущий пользователь сеанса. https://www.postgresql.org/docs/10/sql-set-role.html

Нам нужно сделать текущего пользователя сеанса членом роли:

create role myrole;
set role myrole;
grant myrole to myuser;
set role myrole;

производит:

Role ROLE created.


Error starting at line : 4 in command -
set role myrole
Error report -
ERROR: permission denied to set role "myrole"

Grant succeeded.


Role SET succeeded.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...