Настройка аутентификации через auth proxy
Вы можете настроить Grafana так, чтобы аутентификацию обрабатывал обратный прокси HTTP. Популярные веб-серверы имеют очень обширный список подключаемых модулей аутентификации, и любой из них можно использовать с функцией AuthProxy. Ниже подробно описаны параметры конфигурации для auth proxy.
[auth.proxy]
# Defaults to false, but set to true to enable this feature
enabled = true
# HTTP Header name that will contain the username or email
header_name = X-WEBAUTH-USER
# HTTP Header property, defaults to `username` but can also be `email`
header_property = username
# Set to `true` to enable auto sign up of users who do not exist in Grafana DB. Defaults to `true`.
auto_sign_up = true
# Define cache time to live in minutes
# If combined with Grafana LDAP integration it is also the sync interval
# Set to 0 to always fetch and sync the latest user data
sync_ttl = 15
# Limit where auth proxy requests come from by configuring a list of IP addresses.
# This can be used to prevent users spoofing the X-WEBAUTH-USER header.
# Example `whitelist = 192.168.1.1, 192.168.1.0/24, 2001::23, 2001::0/120`
whitelist =
# Optionally define more headers to sync other user attributes
# Example `headers = Name:X-WEBAUTH-NAME Role:X-WEBAUTH-ROLE Email:X-WEBAUTH-EMAIL Groups:X-WEBAUTH-GROUPS`
headers =
# Non-ASCII strings in header values are encoded using quoted-printable encoding
;headers_encoded = false
# Check out docs on this for more details on the below setting
enable_login_token = false
Взаимодействие с AuthProxy Grafana через curl
curl -H "X-WEBAUTH-USER: admin" http://localhost:3000/api/users
[
{
"id":1,
"name":"",
"login":"admin",
"email":"admin@localhost",
"isAdmin":true
}
]
Затем мы можем отправить второй запрос к методу /api/user, который вернёт сведения о вошедшем в систему пользователе. Мы используем этот запрос, чтобы показать, как Grafana автоматически добавляет указанного нами нового пользователя в систему. Здесь мы создаём нового пользователя с именем «anthony».
curl -H "X-WEBAUTH-USER: anthony" http://localhost:3000/api/user
{
"email":"anthony",
"name":"",
"login":"anthony",
"theme":"",
"orgId":1,
"isGrafanaAdmin":false
}
Совместная работа аутентификации Apache с AuthProxy Grafana
Я продемонстрирую, как использовать Apache для аутентификации пользователей. В этом примере мы используем BasicAuth с основанным на текстовом файле обработчиком аутентификации Apache, то есть файлами htpasswd. Однако можно использовать любые доступные возможности аутентификации Apache.
Apache BasicAuth
В этом примере мы используем Apache в качестве обратного прокси перед Grafana. Apache обрабатывает аутентификацию пользователей, прежде чем переслать запросы в серверную службу Grafana.
Конфигурация Apache
<VirtualHost *:80>
ServerAdmin webmaster@authproxy
ServerName authproxy
ErrorLog "logs/authproxy-error_log"
CustomLog "logs/authproxy-access_log" common
<Proxy *>
AuthType Basic
AuthName GrafanaAuthProxy
AuthBasicProvider file
AuthUserFile /etc/apache2/grafana_htpasswd
Require valid-user
RewriteEngine On
RewriteRule .* - [E=PROXY_USER:%{LA-U:REMOTE_USER},NS]
RequestHeader set X-WEBAUTH-USER "%{PROXY_USER}e"
</Proxy>
RequestHeader unset Authorization
ProxyRequests Off
ProxyPass / http://localhost:3000/
ProxyPassReverse / http://localhost:3000/
</VirtualHost>
-
Первые четыре строки конфигурации virtualhost стандартны, поэтому мы не будем подробно останавливаться на том, что они делают.
-
Мы используем блок конфигурации <proxy> для применения наших правил аутентификации к каждому проксируемому запросу. Эти правила включают требование базовой аутентификации, при которой учётные данные user:password хранятся в файле /etc/apache2/grafana_htpasswd. Этот файл можно создать с помощью команды
htpasswd.- Следующая часть конфигурации — это сложная часть. Мы используем движок перезаписи Apache для создания нашего заголовка X-WEBAUTH-USER, заполненного аутентифицированным пользователем.
-
RewriteRule .* - [E=PROXY_USER:%{LA-U:REMOTE_USER}, NS]: Эта строка — немного магии. Она делает следующее: для каждого запроса использует функцию упреждающего просмотра (LA-U) rewriteEngines, чтобы определить, чему будет равна переменная REMOTE_USER после обработки запроса. Затем присваивает результат переменной PROXY_USER. Это необходимо, поскольку переменная REMOTE_USER недоступна для функции RequestHeader.
-
RequestHeader set X-WEBAUTH-USER “%{PROXY_USER}e”: Теперь, когда аутентифицированное имя пользователя хранится в переменной PROXY_USER, мы создаём новый заголовок запроса HTTP, который будет отправлен нашему серверному Grafana и будет содержать имя пользователя.
-
- Следующая часть конфигурации — это сложная часть. Мы используем движок перезаписи Apache для создания нашего заголовка X-WEBAUTH-USER, заполненного аутентифицированным пользователем.
-
RequestHeader unset Authorization удаляет заголовок Authorization из запроса HTTP до того, как он будет переслан в Grafana. Это гарантирует, что Grafana не попытается аутентифицировать пользователя с помощью этих учётных данных (BasicAuth является поддерживаемым обработчиком аутентификации в Grafana).
-
Последние 3 строки — это просто стандартная конфигурация обратного прокси для направления всех аутентифицированных запросов на наш сервер Grafana, работающий на порту 3000.
Полное пошаговое руководство с использованием Docker
В этом примере мы используем официальный Docker-образ Grafana, доступный на Docker Hub.
- Создайте файл
grafana.iniсо следующим содержимым
[users]
allow_sign_up = false
auto_assign_org = true
auto_assign_org_role = Editor
[auth.proxy]
enabled = true
header_name = X-WEBAUTH-USER
header_property = username
auto_sign_up = true
Запустите контейнер Grafana, используя наш пользовательский grafana.ini для замены /etc/grafana/grafana.ini. Мы не открываем
никаких портов для этого контейнера, так как к нему будет подключаться только наш контейнер Apache.
docker run -i -v $(pwd)/grafana.ini:/etc/grafana/grafana.ini --name grafana grafana/grafana
Контейнер Apache
В этом примере мы используем официальный Docker-образ Apache, доступный на Docker Hub
- Создайте файл с именем
httpd.confсо следующим содержимым
ServerRoot "/usr/local/apache2"
Listen 80
LoadModule mpm_event_module modules/mod_mpm_event.so
LoadModule authn_file_module modules/mod_authn_file.so
LoadModule authn_core_module modules/mod_authn_core.so
LoadModule authz_host_module modules/mod_authz_host.so
LoadModule authz_user_module modules/mod_authz_user.so
LoadModule authz_core_module modules/mod_authz_core.so
LoadModule auth_basic_module modules/mod_auth_basic.so
LoadModule log_config_module modules/mod_log_config.so
LoadModule env_module modules/mod_env.so
LoadModule headers_module modules/mod_headers.so
LoadModule unixd_module modules/mod_unixd.so
LoadModule rewrite_module modules/mod_rewrite.so
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_http_module modules/mod_proxy_http.so
<IfModule unixd_module>
User daemon
Group daemon
</IfModule>
ServerAdmin you@example.com
<Directory />
AllowOverride none
Require all denied
</Directory>
DocumentRoot "/usr/local/apache2/htdocs"
ErrorLog /proc/self/fd/2
LogLevel error
<IfModule log_config_module>
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b" common
<IfModule logio_module>
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\" %I %O" combinedio
</IfModule>
CustomLog /proc/self/fd/1 common
</IfModule>
<Proxy *>
AuthType Basic
AuthName GrafanaAuthProxy
AuthBasicProvider file
AuthUserFile /tmp/htpasswd
Require valid-user
RewriteEngine On
RewriteRule .* - [E=PROXY_USER:%{LA-U:REMOTE_USER},NS]
RequestHeader set X-WEBAUTH-USER "%{PROXY_USER}e"
</Proxy>
RequestHeader unset Authorization
ProxyRequests Off
ProxyPass / http://grafana:3000/
ProxyPassReverse / http://grafana:3000/
-
Создайте файл
htpasswd. Мы создаём нового пользователя anthony с паролем passwordhtpasswd -bc htpasswd anthony password -
Запустите контейнер HTTP-сервера Apache, используя наш пользовательский
httpd.confи наш файлhtpasswd. Контейнер будет слушать порт 80, и мы создаём ссылку на контейнер grafana, чтобы этот контейнер мог разрешить имя хоста grafana в IP-адрес контейнера Grafana.docker run -i -p 80:80 --link grafana:grafana -v $(pwd)/httpd.conf:/usr/local/apache2/conf/httpd.conf -v $(pwd)/htpasswd:/tmp/htpasswd httpd:2.4
Использование Grafana
Когда наши контейнеры Grafana и Apache запущены, вы можете подключиться к http://localhost/ и войти, используя имя пользователя и пароль, которые мы создали в файле htpasswd.
Note
Если пользователь удалён из Grafana, он не сможет войти в систему и выполнить повторную синхронизацию, пока не истечёт
sync_ttl.
Синхронизация команд
Note
Доступно в Grafana Enterprise и для клиентов на отдельных планах Grafana Cloud. Информацию о ценах см. на странице цены или свяжитесь с нашей командой продаж.
С синхронизацией команд можно настроить синхронизацию между командами в вашем провайдере аутентификации и Grafana. Вы можете отправлять значения Grafana как часть заголовка HTTP, и Grafana сопоставит их с вашей структурой команд. Это позволяет автоматически помещать пользователей в определённые команды.
Для поддержки этой функции auth proxy допускает необязательные заголовки для сопоставления дополнительных атрибутов пользователя. Конкретный атрибут для поддержки синхронизации команд — Groups.
# Optionally define more headers to sync other user attributes
headers = "Groups:X-WEBAUTH-GROUPS"
Вы используете заголовок X-WEBAUTH-GROUPS для отправки информации о команде для каждого пользователя. В частности, набора group ID Grafana, к которым принадлежит пользователь.
Во-первых, нам нужно настроить сопоставление между вашим провайдером аутентификации и Grafana. Следуйте этим инструкциям, чтобы добавить группы в команду внутри Grafana.
После этого вы можете проверить свои сопоставления, запросив API.
# First, inspect your teams and obtain the corresponding ID of the team we want to inspect the groups for.
curl -H "X-WEBAUTH-USER: admin" -H "X-WEBAUTH-GROUPS: lokiteamOnExternalSystem" http://localhost:3000/api/teams/search
{
"totalCount": 2,
"teams": [
{
"id": 1,
"orgId": 1,
"name": "Core",
"email": "core@grafana.com",
"avatarUrl": "/avatar/327a5353552d2dc3966e2e646908f540",
"memberCount": 1,
"permission": 0
},
{
"id": 2,
"orgId": 1,
"name": "Loki",
"email": "loki@grafana.com",
"avatarUrl": "/avatar/102f937d5344d33fdb37b65d430f36ef",
"memberCount": 0,
"permission": 0
}
],
"page": 1,
"perPage": 1000
}
# Then, query the groups for that particular team. In our case, the Loki team which has an ID of "2".
curl -H "X-WEBAUTH-USER: admin" -H "X-WEBAUTH-GROUPS: lokiteamOnExternalSystem" http://localhost:3000/api/teams/2/groups
[
{
"orgId": 1,
"teamId": 2,
"groupId": "lokiTeamOnExternalSystem"
}
]
Наконец, всякий раз, когда Grafana получает запрос с заголовком X-WEBAUTH-GROUPS: lokiTeamOnExternalSystem, аутентифицируемый пользователь будет помещён в указанную команду. Помещение в несколько команд поддерживается с помощью значений, разделённых запятыми, например lokiTeamOnExternalSystem,CoreTeamOnExternalSystem.
curl -H "X-WEBAUTH-USER: leonard" -H "X-WEBAUTH-GROUPS: lokiteamOnExternalSystem" http://localhost:3000/dashboards/home
{
"meta": {
"isHome": true,
"canSave": false,
...
}
Таким образом, пользователь leonard будет автоматически помещён в команду Loki в рамках аутентификации Grafana.
Note
Пустой
X-WEBAUTH-GROUPSили отсутствие заголовка групп удалит пользователя из всех команд.
Узнать больше о синхронизации команд
Токен входа и cookie сессии
Когда enable_login_token установлен в true, Grafana после успешной проверки заголовка auth proxy назначит пользователю
токен входа и cookie. Вам нужно настроить ваш auth proxy так, чтобы он предоставлял заголовки только для маршрута /login.
Запросы через другие маршруты будут аутентифицироваться с помощью cookie.
Используйте настройки login_maximum_inactive_lifetime_duration и login_maximum_lifetime_duration в разделе [auth] для управления сроком
жизни сессии.