Spec-Zone.ru › MySQL 5.7

6.2.14 Пользователи-прокси

Сервер MySQL аутентифицирует подключения клиентов с помощью плагинов аутентификации. Плагин, аутентифицирующий данное подключение, может запросить, чтобы подключаемый (внешний) пользователь рассматривался как другой пользователь для целей проверки привилегий. Это позволяет внешнему пользователю выступать в качестве прокси для второго пользователя; то есть, принять на себя привилегии второго пользователя:

  • Внешний пользователь является “пользователем-прокси” (пользователь, который может имитировать или стать известным как другой пользователь).

  • Второй пользователь является “пользователем-целью” (пользователь, чья личность и привилегии могут быть приняты пользователем-прокси).

Этот раздел описывает, как работает механизм пользователей-прокси. Для общей информации о плагинах аутентификации см. Раздел 6.2.13, «Плагиновая аутентификация». Для информации о конкретных плагинах см. Раздел 6.4.1, «Плагины аутентификации». Для получения информации об написании плагинов аутентификации, поддерживающих пользователей-прокси, см. Реализация поддержки пользователей-прокси в плагинах аутентификации.

  • Требования к поддержке пользователей-прокси

  • Пример простого пользователя-прокси

  • Предотвращение прямого входа в учётные записи-цели

  • Предоставление и отозвaние привилегии PROXY

  • Пользователи-прокси по умолчанию

  • Конфликты между пользователями-прокси по умолчанию и анонимными пользователями

  • Поддержка сервера для сопоставления пользователей-прокси

  • Системные переменные для пользователей-прокси

Требования к поддержке пользователей-прокси

Для того, чтобы проксирование работало для данного плагина аутентификации, должны быть выполнены следующие условия:

  • Проксирование должно быть поддерживаемо, либо самим плагином, либо сервером MySQL от имени плагина. В последнем случае, поддержка сервера может потребовать явного включения; см. Поддержка сервера для сопоставления пользователей-прокси.

  • Учётная запись внешнего пользователя-прокси должна быть настроена для аутентификации плагином. Используйте оператор CREATE USER для ассоциации учётной записи с плагином аутентификации или ALTER USER для изменения плагина.

  • Учётная запись пользователя-цели должна существовать и иметь привилегии, которые должен принять пользователь-прокси. Используйте операторы CREATE USER и GRANT для этого.

  • Обычно пользователь-цель настраивается так, чтобы его можно было использовать только в сценариях проксирования, а не для прямого входа.

  • Учётная запись пользователя-прокси должна иметь привилегию PROXY для учётной записи-цели. Используйте оператор GRANT для этого.

  • Для того, чтобы клиент, подключающийся к учётной записи-прокси, обрабатывался как пользователь-прокси, плагин аутентификации должен возвращать имя пользователя, отличное от имени пользователя клиента, чтобы указать имя пользователя учётной записи-цели, определяющее привилегии, которые должен принять пользователь-прокси.

    В качестве альтернативы, для плагинов, которым сервер предоставляет сопоставление проксирования, пользователь-цель определяется по привилегии PROXY, имеемой пользователем-прокси.

Механизм проксирования допускает сопоставление только имени внешнего пользователя-клиента с именем пользователя-цели. Нет возможности сопоставления имён хостов:

  • При подключении клиента к серверу, сервер определяет соответствующую учётную запись на основе имени пользователя, переданного программой-клиентом, и хоста, с которого клиент подключается.

  • Если эта учётная запись является учётной записью-прокси, сервер пытается определить соответствующую учётную запись-цель, найдя соответствие для учётной записи-цели с использованием имени пользователя, возвращённого плагином аутентификации, и имени хоста учётной записи-прокси. Имя хоста в учётной записи-цели игнорируется.

Пример простого пользователя-прокси

Рассмотрим следующие определения учётных записей:

-- create proxy account
CREATE USER 'employee_ext'@'localhost'
  IDENTIFIED WITH my_auth_plugin
  AS 'my_auth_string';

-- create proxied account and grant its privileges;
-- use mysql_no_login plugin to prevent direct login
CREATE USER 'employee'@'localhost'
  IDENTIFIED WITH mysql_no_login;
GRANT ALL
  ON employees.*
  TO 'employee'@'localhost';

-- grant to proxy account the
-- PROXY privilege for proxied account
GRANT PROXY
  ON 'employee'@'localhost'
  TO 'employee_ext'@'localhost';

Когда клиент подключается как employee_ext с локального хоста, MySQL использует плагин под названием my_auth_plugin для выполнения аутентификации. Предположим, что my_auth_plugin возвращает имя пользователя employee серверу, основываясь на содержании 'my_auth_string' и, возможно, консультируясь с какой-либо внешней системой аутентификации. Имя employee отличается от employee_ext, поэтому возвращение employee служит запросом серверу о том, чтобы рассматривать внешнего пользователя employee_ext для целей проверки привилегий как локального пользователя employee.

В этом случае employee_ext является пользователем-прокси, а employee - пользователем-целью.

Сервер проверяет, возможно ли проксирование аутентификации для employee для пользователя employee_ext, проверив, имеет ли employee_ext (пользователь-прокси) привилегию PROXY для employee (пользователя-цели). Если эта привилегия не предоставлена, возникает ошибка. В противном случае, employee_ext принимает на себя привилегии employee. Сервер проверяет запросы, выполненные во время сессии клиента от имени employee_ext, по отношению к привилегиям, предоставленным employee. В данном случае, employee_ext может получить доступ к таблицам базы данных employees.

Учётная запись-цель, employee, использует плагин аутентификации mysql_no_login, чтобы предотвратить клиентам прямой вход в неё. (Предполагается, что плагин установлен. Инструкции см. в Разделе 6.4.1.10, «Аутентификация без входа с использованием плагинов».) Для альтернативных методов защиты учётных записей-цели от прямого использования, см. Предотвращение прямого входа в учётные записи-цели.

При проксировании можно использовать функции USER() и CURRENT_USER(), чтобы увидеть разницу между подключающимся пользователем (пользователем-прокси) и учётной записью, чьи привилегии применяются во время текущей сессии (пользователем-целью). Для описанного выше примера, эти функции возвращают следующие значения:

mysql> SELECT USER(), CURRENT_USER();
+------------------------+--------------------+
| USER()                 | CURRENT_USER()     |
+------------------------+--------------------+
| employee_ext@localhost | employee@localhost |
+------------------------+--------------------+

В операторе CREATE USER, создающем учётную запись пользователя-прокси, клаузу IDENTIFIED WITH, указывающую плагин аутентификации, поддерживающий проксирование, можно необязательно дополнить клаузой AS 'auth_string', задающей строку, которую сервер передаёт плагину при подключении пользователя. При наличии, строка предоставляет информацию, которая помогает плагину определить, как сопоставить имя пользователя-прокси (внешнего) клиента с именем пользователя-цели. От каждого плагина зависит, требует ли он клаузу AS. Если да, то формат строки аутентификации зависит от того, как плагин намерен её использовать. Обратитесь к документации для конкретного плагина для получения информации о значениях строк аутентификации, которые он принимает.

Предотвращение прямого входа в прокси-аккаунты

Прокси-аккаунты, как правило, предназначены для использования только через прокси-аккаунты. То есть клиенты подключаются с помощью прокси-аккаунта, затем им назначаются права соответствующего прокси-пользователя.

Существует несколько способов гарантировать, что прокси-аккаунт нельзя использовать напрямую:

  • Свяжите аккаунт с плагином аутентификации mysql_no_login. В этом случае аккаунт нельзя использовать для прямого входа ни при каких обстоятельствах. Предполагается, что плагин установлен. Инструкции см. в разделе 6.4.1.10 «No-Login Pluggable Authentication».

  • Включите опцию ACCOUNT LOCK при создании аккаунта. См. раздел 13.7.1.2 «CREATE USER Statement». В этом методе также укажите пароль, чтобы, если аккаунт будет разблокирован позже, к нему нельзя было получить доступ без пароля. (Если плагин validate_password включен, он не позволяет создавать аккаунт без пароля, даже если аккаунт заблокирован. См. раздел 6.4.3 «The Password Validation Plugin».)

  • Создайте аккаунт с паролем, но не сообщайте пароль другим. Если вы не сообщите пароль аккаунта никому, клиенты не смогут использовать его для прямого подключения к серверу MySQL.

Предоставление и отзыв привилегии PROXY

Привилегия PROXY необходима, чтобы разрешить внешнему пользователю подключиться как другой пользователь и получить его права. Для предоставления этой привилегии используйте оператор GRANT. Например:

GRANT PROXY ON 'proxied_user' TO 'proxy_user';

Этот оператор создает строку в таблице разрешений mysql.proxies_priv.

Во время подключения proxy_user должен представлять действительного внешне аутентифицированного пользователя MySQL, а proxied_user — действительного локально аутентифицированного пользователя. В противном случае попытка подключения завершится неудачей.

Соответствующая синтаксис оператора REVOKE:

REVOKE PROXY ON 'proxied_user' FROM 'proxy_user';

Расширения синтаксиса MySQL GRANT и REVOKE работают как обычно. Примеры:

-- grant PROXY to multiple accounts
GRANT PROXY ON 'a' TO 'b', 'c', 'd';

-- revoke PROXY from multiple accounts
REVOKE PROXY ON 'a' FROM 'b', 'c', 'd';

-- grant PROXY to an account and enable the account to grant
-- PROXY to the proxied account
GRANT PROXY ON 'a' TO 'd' WITH GRANT OPTION;

-- grant PROXY to default proxy account
GRANT PROXY ON 'a' TO ''@'';

Привилегия PROXY может быть предоставлена в следующих случаях:

  • Пользователем, имеющим GRANT PROXY ... WITH GRANT OPTION для proxied_user.

  • Самим proxied_user: значение функции USER() должно точно совпадать со значением функции CURRENT_USER() и proxied_user, как для имени пользователя, так и для имени хоста аккаунта.

Изначальный аккаунт root, созданный во время установки MySQL, имеет привилегию PROXY ... WITH GRANT OPTION для ''@'', то есть для всех пользователей и всех хостов. Это позволяет root настраивать прокси-пользователей, а также делегировать другим аккаунтам право на настройку прокси-пользователей. Например, root может сделать это:

CREATE USER 'admin'@'localhost'
  IDENTIFIED BY 'admin_password';
GRANT PROXY
  ON ''@''
  TO 'admin'@'localhost'
  WITH GRANT OPTION;

Эти операторы создают пользователя admin, который может управлять всеми отображениями GRANT PROXY. Например, admin может сделать это:

GRANT PROXY ON sally TO joe;

Пользователи-прокси по умолчанию

Чтобы указать, что некоторые или все пользователи должны подключаться с использованием данного плагина аутентификации, создайте «пустой» аккаунт MySQL с пустым именем пользователя и хоста (''@''), свяжите его с этим плагином и позвольте плагину вернуть действительное имя аутентифицированного пользователя (если оно отличается от пустого имени пользователя). Предположим, что существует плагин под названием ldap_auth, реализующий аутентификацию LDAP и сопоставляющий подключающихся пользователей либо с аккаунтом разработчика, либо с аккаунтом менеджера. Чтобы настроить проксирование пользователей на эти аккаунты, используйте следующие операторы:

-- create default proxy account
CREATE USER ''@''
  IDENTIFIED WITH ldap_auth
  AS 'O=Oracle, OU=MySQL';

-- create proxied accounts; use
-- mysql_no_login plugin to prevent direct login
CREATE USER 'developer'@'localhost'
  IDENTIFIED WITH mysql_no_login;
CREATE USER 'manager'@'localhost'
  IDENTIFIED WITH mysql_no_login;

-- grant to default proxy account the
-- PROXY privilege for proxied accounts
GRANT PROXY
  ON 'manager'@'localhost'
  TO ''@'';
GRANT PROXY
  ON 'developer'@'localhost'
  TO ''@'';

Теперь предположим, что клиент подключается следующим образом:

$> mysql --user=myuser --password ...
Enter password: myuser_password

Сервер не находит myuser как пользователя MySQL, но поскольку существует пустой аккаунт пользователя (''@''), который соответствует имени пользователя и имени хоста клиента, сервер аутентифицирует клиента по этому аккаунту: Сервер вызывает плагин аутентификации ldap_auth и передает ему myuser и myuser_password в качестве имени пользователя и пароля.

Если плагин ldap_auth обнаружит в каталоге LDAP, что myuser_password не является правильным паролем для myuser, аутентификация завершится неудачей, и сервер отклонит подключение.

Если пароль верен и ldap_auth обнаружит, что myuser — это разработчик, он вернет имя пользователя developer серверу MySQL вместо myuser. Возврат имени пользователя, отличного от имени пользователя клиента myuser, сигнализирует серверу о том, что он должен обрабатывать myuser как прокси. Сервер проверяет, что ''@'' может пройти аутентификацию как developer (поскольку у ''@'' есть привилегия PROXY для этого) и принимает подключение. Сессия продолжается с myuser, имеющим права прокси-пользователя developer (эти права должны быть настроены администратором базы данных с помощью операторов GRANT, которые здесь не показаны). Функции USER() и CURRENT_USER() возвращают эти значения:

mysql> SELECT USER(), CURRENT_USER();
+------------------+---------------------+
| USER()           | CURRENT_USER()      |
+------------------+---------------------+
| myuser@localhost | developer@localhost |
+------------------+---------------------+

Если плагин вместо этого обнаружит в каталоге LDAP, что myuser — это менеджер, он вернет manager в качестве имени пользователя, и сессия продолжится с myuser, имеющим права прокси-пользователя manager.

mysql> SELECT USER(), CURRENT_USER();
+------------------+-------------------+
| USER()           | CURRENT_USER()    |
+------------------+-------------------+
| myuser@localhost | manager@localhost |
+------------------+-------------------+

Для простоты внешняя аутентификация не может быть многоуровневой: ни учетные данные для developer, ни для manager не учитываются в приведенном примере. Однако они все еще используются, если клиент пытается подключиться и пройти аутентификацию непосредственно как аккаунт developer или manager, поэтому эти прокси-аккаунты должны быть защищены от прямого входа (см. Предотвращение прямого входа в прокси-аккаунты).

Конфликты пользователя-прокси по умолчанию и анонимного пользователя

Если вы намерены создать пользователя-прокси по умолчанию, проверьте наличие других учётных записей “соответствующих любому пользователю”, которые имеют приоритет над пользователем-прокси по умолчанию, так как они могут препятствовать его корректной работе.

В предыдущем обсуждении учётная запись пользователя-прокси по умолчанию имеет '' в части хоста, что соответствует любому хосту. Если вы настраиваете пользователя-прокси по умолчанию, обратите внимание на наличие учётных записей без прокси с той же частью пользователя и '%' в части хоста, так как '%' также соответствует любому хосту, но имеет приоритет над '' по правилам, используемым сервером для сортировки строк учётных записей (см. Раздел 6.2.5, «Управление доступом, этап 1: Проверка подключения»).

Предположим, что установка MySQL включает эти две учётные записи:

-- create default proxy account
CREATE USER ''@''
  IDENTIFIED WITH some_plugin
  AS 'some_auth_string';
-- create anonymous account
CREATE USER ''@'%'
  IDENTIFIED BY 'anon_user_password';

Первая учётная запись (''@'') предназначена как пользователь-прокси по умолчанию, используемый для аутентификации подключений для пользователей, которые не соответствуют более конкретной учётной записи. Вторая учётная запись (''@'%') — это учётная запись анонимного пользователя, которая могла быть создана, например, для обеспечения возможности подключения анонимно пользователям без собственной учётной записи.

Обе учётные записи имеют ту же часть пользователя (''), которая соответствует любому пользователю. И каждая учётная запись имеет часть хоста, соответствующую любому хосту. Тем не менее, существует приоритет в соответствии учётных записей для попыток подключения, так как правила сопоставления сортируют хост '%' перед ''. Для учётных записей, которые не соответствуют никакой более конкретной учётной записи, сервер пытается выполнить аутентификацию по ''@'%' (анонимному пользователю), а не по ''@'' (пользователю-прокси по умолчанию). В результате учётная запись пользователя-прокси по умолчанию никогда не используется.

Чтобы избежать этой проблемы, используйте одну из следующих стратегий:

  • Удалите анонимную учётную запись, чтобы она не конфликтовала с пользователем-прокси по умолчанию.

  • Используйте более конкретного пользователя-прокси по умолчанию, который соответствует раньше анонимного пользователя. Например, для разрешения только подключений прокси localhost, используйте ''@'localhost':

    CREATE USER ''@'localhost'
      IDENTIFIED WITH some_plugin
      AS 'some_auth_string';
    

    Кроме того, измените все GRANT PROXY операторы, чтобы назвать ''@'localhost', а не ''@'', как пользователя-прокси.

    Обратите внимание, что эта стратегия предотвращает подключения анонимных пользователей от localhost.

  • Используйте именованную учётную запись по умолчанию вместо анонимной учётной записи по умолчанию. Для примера этого метода обратитесь к инструкциям по использованию плагина authentication_windows. См. Раздел 6.4.1.8, «Подключение Windows».

  • Создайте нескольких пользователей-прокси, одного для локальных подключений и одного для “всего остального” (удалённых подключений). Это может быть полезно, особенно когда локальные пользователи должны иметь разные привилегии от удалённых пользователей.

    Создайте пользователей-прокси:

    -- create proxy user for local connections
    CREATE USER ''@'localhost'
      IDENTIFIED WITH some_plugin
      AS 'some_auth_string';
    -- create proxy user for remote connections
    CREATE USER ''@'%'
      IDENTIFIED WITH some_plugin
      AS 'some_auth_string';
    

    Создайте прокси-пользователей:

    -- create proxied user for local connections
    CREATE USER 'developer'@'localhost'
      IDENTIFIED WITH mysql_no_login;
    -- create proxied user for remote connections
    CREATE USER 'developer'@'%'
      IDENTIFIED WITH mysql_no_login;
    

    Предоставьте каждой учётной записи-прокси привилегию PROXY для соответствующей учётной записи-прокси:

    GRANT PROXY
      ON 'developer'@'localhost'
      TO ''@'localhost';
    GRANT PROXY
      ON 'developer'@'%'
      TO ''@'%';
    

    Наконец, предоставьте соответствующие привилегии локальным и удалённым пользователям-прокси (не показано).

    Предположим, что сочетание some_plugin/'some_auth_string' приводит к тому, что some_plugin сопоставляет имя пользователя клиента с developer. Локальные подключения соответствуют пользователю-прокси ''@'localhost', который сопоставляется с пользователем-прокси 'developer'@'localhost'. Удалённые подключения соответствуют пользователю-прокси ''@'%', который сопоставляется с пользователем-прокси 'developer'@'%'.

Поддержка сервера для сопоставления пользователей-прокси

Некоторые плагины аутентификации реализуют сопоставление пользователей-прокси для себя (например, плагины аутентификации PAM и Windows). Другие плагины аутентификации по умолчанию не поддерживают пользователей-прокси. Из них некоторые могут запросить, чтобы сам сервер MySQL сопоставлял пользователей-прокси в соответствии с предоставленными привилегиями прокси: mysql_native_password, sha256_password. Если переменная системы check_proxy_users включена, сервер выполняет сопоставление пользователей-прокси для любых плагинов аутентификации, которые делают такой запрос:

  • По умолчанию check_proxy_users отключена, поэтому сервер не выполняет сопоставление пользователей-прокси даже для плагинов аутентификации, которые запрашивают поддержку сервера для пользователей-прокси.

  • Если check_proxy_users включена, может потребоваться включить специфичную для плагина переменную системы, чтобы воспользоваться поддержкой сопоставления пользователей-прокси сервера:

    • Для плагина mysql_native_password включите mysql_native_password_proxy_users.

    • Для плагина sha256_password включите sha256_password_proxy_users.

Например, чтобы включить все перечисленные возможности, запустите сервер с этими строками в файле my.cnf:

[mysqld]
check_proxy_users=ON
mysql_native_password_proxy_users=ON
sha256_password_proxy_users=ON

Предполагая, что соответствующие переменные системы включены, создайте пользователя-прокси как обычно с помощью CREATE USER, затем предоставьте ему привилегию PROXY для одной другой учётной записи, которая будет рассматриваться как пользователь-прокси. Когда сервер получает успешный запрос на подключение для пользователя-прокси, он обнаруживает, что пользователь обладает привилегией PROXY и использует её для определения соответствующего пользователя-прокси.

-- create proxy account
CREATE USER 'proxy_user'@'localhost'
  IDENTIFIED WITH mysql_native_password
  BY 'password';

-- create proxied account and grant its privileges;
-- use mysql_no_login plugin to prevent direct login
CREATE USER 'proxied_user'@'localhost'
  IDENTIFIED WITH mysql_no_login;
-- grant privileges to proxied account
GRANT ...
  ON ...
  TO 'proxied_user'@'localhost';

-- grant to proxy account the
-- PROXY privilege for proxied account
GRANT PROXY
  ON 'proxied_user'@'localhost'
  TO 'proxy_user'@'localhost';

Чтобы использовать учётную запись-прокси, подключитесь к серверу с помощью её имени и пароля:

$> mysql -u proxy_user -p
Enter password: (enter proxy_user password here)

Аутентификация проходит успешно, сервер обнаруживает, что proxy_user обладает привилегией PROXY для proxied_user, и сессия продолжается с proxy_user, имеющим привилегии proxied_user.

Сопоставление пользователей-прокси, выполняемое сервером, ограничено следующими условиями:

  • Сервер не выполняет проксирование к или от анонимного пользователя, даже если соответствующая привилегия PROXY предоставлена.

  • Когда одной учётной записи предоставлены привилегии проксирования для более чем одной учётной записи-прокси, сопоставление пользователей-прокси сервером не является детерминированным. Поэтому предоставление одной учётной записи привилегий проксирования для нескольких учётных записей-прокси не рекомендуется.

Переменные системы пользователей-прокси

Две переменные системы помогают отследить процесс входа пользователя-прокси:

  • proxy_user: Это значение равно NULL, если проксирование не используется. В противном случае оно указывает учётную запись пользователя-прокси. Например, если клиент выполняет аутентификацию через учётную запись-прокси ''@'', эта переменная устанавливается следующим образом:

    mysql> SELECT @@proxy_user;
    +--------------+
    | @@proxy_user |
    +--------------+
    | ''@''        |
    +--------------+
    
  • external_user: Иногда плагин аутентификации может использовать внешнего пользователя для аутентификации на сервере MySQL. Например, при использовании аутентификации Windows нативными средствами, плагин, который выполняет аутентификацию с помощью API Windows, не нуждается в том, чтобы идентификатор входа передавался ему. Однако он по-прежнему использует идентификатор пользователя Windows для аутентификации. Плагин может возвратить этот внешний идентификатор пользователя (или первые 512 байтов UTF-8) серверу с помощью переменной сессии только для чтения external_user. Если плагин не установил эту переменную, её значение равно NULL.

© 2025 Oracle
Licensed under the GPLv2 License.
https://docs.oracle.com/cd/E17952_01/mysql-5.7-en/proxy-users.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API