В любом проекте возникает необходимость ограничения доступа к определенным частям приложения. Веб‑сервер Angie предоставляет разнообразные возможности решения этой задачи с помощью стандартных (встроенных) и сторонних модулей, которые мы будем разбирать в этой статье.
Навигация по циклу
Настройка location в Angie. Разделение динамических и статических запросов.
Перенаправления в Angie: return, rewrite и примеры их применения.
Сжатие текста в Angie: статика, динамика, производительность.
Контроль доступа в Angie.
Видеоверсия
Для вашего удобства подготовлена видеоверсия этой статьи, доступна на Rutube, VKVideo и YouTube.
Базовая HTTP-аутентификация
Начнём с самого простого в настройке метода ограничения доступа — стандартного модуля Auth Basic. Он использует файл с логинами и паролями пользователей в формате .htpasswd.
Первое действие для использования такого метода: создать файл с паролями. Для этого можно использовать утилиту htpasswd (входит в комплект утилит Apache) или формировать пароль самостоятельно с помощью команды openssl passwd. Ниже представлены оба метода:
htpasswd -c /etc/angie/htpasswd newuser
echo -n 'testuser:' >> /etc/angie/.htpasswd
openssl passwd -apr1 >> /etc/angie/.htpasswdВ нашем случае использовался стандартный метод хэширования MD5 в формате apr1, но поддерживаются и другие варианты. На выходе мы получаем файл с указанием пользователей построчно, логин и хэш пароля разделены двоеточием.
testuser:$apr1$lE18tH5l$hAaBMjBG7OwSOhdoqIdC.0
newuser:$apr1$DnNBSOwt$mLRu5H4izpPsvqxKEQgXo0Теперь мы можем использовать этот файл для ограничения доступа к серверу или локации (возможные контексты: http, server, location, limit_except). Для этого достаточно указать файл с пользователями и название зоны доступа, как в примере ниже:
location / {
auth_basic "Identify yourself!";
auth_basic_user_file /etc/angie/.htpasswd;
}Если необходимо отключить действие директивы auth_basic (запрос пароля), унаследованной от родительского блока конфигурации, существует специальное значение off. Например, доступ к серверу будет закрыт аутентификацией, а отдельная локация /static/ будет доступна свободно.
server {
auth_basic "Identify yourself!";
auth_basic_user_file /etc/angie/.htpasswd;
location /static/ {
auth_basic off;
}
}Важно помнить, что метод HTTP‑аутентификации Basic передаёт логин и пароль в открытом виде, поэтому его стоит использовать совместно с HTTPS, чтобы исключить перехват данных при аутентификации. Также отсутствует возможность управления списками пользователей для доступа. Всем пользователям, перечисленным в файле, доступ будет разрешен. Если нужно разделять доступ по группам пользователей, потребуется создать несколько файлов (один для каждой группы).
Контроль доступа по IP
Часто ограничение доступа к сайтам реализуются на основе IP‑адреса клиента. Для контроля доступа в этом случае мы используем стандартный модуль Access.
Правила доступа обрабатываются в порядке следования в конфиге до первого совпадения. Поэтому для корректной работы сначала перечисляются более точечные правила разрешения или запрета доступа, а потом общее правило для всех остальных. Разберём пример:
location /sec/ {
deny 192.168.0.100;
allow 192.168.0.0/24;
deny all;
}Здесь мы запрещаем доступ с IP 192.168.0.100, при этом для всех остальных адресов сети 192.168.0.0/24 доступ разрешен. Далее установлено ограничение доступа для всех остальных адресов клиентов (deny all).
Ограничения по списку пользователей и адресам можно использовать совместно. Для этого потребуется директива satisfy, которая будет определять логику совместного использования проверок. При значении all (по умолчанию) необходимо пройти все проверки (список пользователей, Auth Request и по адресам). Значение any разрешает доступ при хотя бы одной успешной проверке. Пример объединения методов контроля доступа.
location /sec/ {
satisfy any;
deny 192.168.0.100;
allow 192.168.0.0/24;
deny all;
auth_basic "Identify yourself!";
auth_basic_user_file /etc/angie/.htpasswd;
}В конфигурации выше доступ получат клиенты из подсети 192.168.0.0/24 (кроме 192.168.0.100) или прошедшие аутентификацию по списку пользователей из файла /etc/angie/.htpasswd.
Аутентификация с помощью Auth Request
Для реализации гибкой системы управления доступом можно использовать стандартный модуль Auth Request. Он формирует внутренний запрос по протоколу HTTP для определения прав доступа. На основании кода ответа на этот запрос доступ разрешается (код 200) или запрещается (401 или 403). Остальные коды ответа интерпретируются как ошибка.
При этом реализация логики может быть на любом языке программирования, специальных ограничений нет, главное — это возврат корректных кодов ответа.
В качестве встроенного решения можно использовать реализацию на основе NJS, подмножества языка JavaScript, исполняемого в самом Angie при подключении соответствующего модуля.
Пример конфигурации с использованием NJS:
js_path "/etc/angie/njs/";
js_import main from http/authorization/auth_request.js;
resolver 1.1.1.1;
upstream backend {
server 127.0.0.1:8091;
}
server {
listen 80;
location /secure/ {
auth_request /validate;
proxy_pass http://backend;
}
location /validate {
internal;
js_content main.authorize;
}
}
server {
listen 127.0.0.1:8091;
return 200 "BACKEND:$uri\n";
}В примере защищается локация /secure/. При попытке доступа происходит внутренний запрос на локацию /validate. Там обработка производится с помощью njs‑функции authorize. Код auth_request.js:
function authorize(r) {
var signature = r.headersIn.Signature;
if (!signature) {
r.error("No signature");
r.return(401);
return;
}
if (r.method != 'GET') {
r.error(`Unsupported method: ${r.method}`);
r.return(401);
return;
}
var args = r.variables.args;
var h = require('crypto').createHmac('sha1', 'foo');
h.update(r.uri).update(args ? args : "");
var req_sig = h.digest("base64");
if (req_sig != signature) {
r.error(`Invalid signature: ${req_sig}\n`);
r.return(401);
return;
}
r.return(200);
}
export default {authorize}Логика проверки аутентификации основана на создании подписи HMAC (Hash‑based Message Authentication Code) c использованием секретного ключа (foo) и алгоритма хэширования SHA1. Поверх происходит кодирование подписи в Base64. Для проверки можно использовать следующие команды (третий вариант должен дать положительный результат):
curl http://localhost/secure/B
curl http://localhost/secure/B -H Signature:fk9WRmw7Rl+NwVAA759+H2Uq
curl http://localhost/secure/B -H Signature:fk9WRmw7Rl+NwVAA759+H2UqxNs=Другие примеры применения NJS для аутентификации и не только можно найти в стороннем репозитории.
Модуль Auth JWT
Переходим к сторонним модулям аутентификации. Первым выступает модуль Auth JWT. Он предоставляет возможность аутентификации с помощью специальных токенов JSON Web Token (JWT). Модуль поддерживает JSON Web Signature (JWS) и может использоваться для работы с протоколом OpenID Connect. Полная документация модуля находится на странице проекта. Установка модуля доступна из репозитория Angie:
apt|dnf install angie-module-auth-jwtПодключаем модуль в главном (main) контексте:
load_module modules/ngx_http_auth_jwt_module.so;Минимальная конфигурация будет выглядеть примерно так:
location / {
auth_jwt "closed site";
auth_jwt_key_file conf/keys.json;
}Директива auth_jwt отвечает за подключение проверки подписей с модуля Auth JWT. Вторая директива auth_jwt_key_file указывает на файл с ключами, используемыми для проверки подписей. В этом файле поддерживаются форматы jwks (JSON Web Key Set — по умолчанию) и keyval.
Модуль Auth SPNEGO
Сторонний модуль Auth SPNEGO позволяет использовать протокол SPNEGO (Simple and Protected GSS API Negotiation Mechanism) для аутентификации с использованием Kerberos и GSS API. В целом идея протокола заключается в согласовании поддерживаемых методов аутентификации в рамках GSS API между клиентом и сервером. Документация модуля доступна в репозитории проекта.
Установка модуля доступна из репозитория Angie:
apt|dnf install angie-module-auth-spnegoПодключаем модуль в главном (main) контексте:
load_module modules/ngx_http_auth_spnego_module.so;Обязательные директивы для работы:
auth_gss: (on/off)— включение модуля;auth_gss_keytab— путь к keytab-файлу.
Если клиент не согласовал метод аутентификации, происходит откат на базовую аутентификацию; чтобы отключить такое поведение, нужно использовать следующую директиву:
auth_gss_allow_basic_fallback off;Пример использования модуля совместно со службой samba можно найти в этой статье.
Модуль Auth LDAP
Еще один вариант контроля доступа — интеграция Angie с LDAP‑сервером. Реализует поддержку LDAP (Lightweight Directory Access Protocol) сторонний модуль Auth LDAP.
Установка модуля доступна из репозитория Angie:
apt|dnf install angie-module-auth-ldapПодключаем модуль в главном (main) контексте:
load_module modules/ngx_http_auth_ldap_module.so;Пример конфигурации двух LDAP‑серверов с требованиями к пользователям и группам:
http {
ldap_server test1 {
url ldap://192.168.0.1:3268/DC=test,DC=local?sAMAccountName?sub?(objectClass=person);
binddn "TEST\\LDAPUSER";
binddn_passwd LDAPPASSWORD;
group_attribute uniquemember;
group_attribute_is_dn on;
require valid_user;
}
ldap_server test2 {
url ldap://192.168.0.2:3268/DC=test,DC=local?sAMAccountName?sub?(objectClass=person);
binddn "TEST\\LDAPUSER";
binddn_passwd LDAPPASSWORD;
group_attribute uniquemember;
group_attribute_is_dn on;
require valid_user;
}
server {
listen 8000;
server_name localhost;
auth_ldap "Forbidden";
auth_ldap_servers test1;
auth_ldap_servers test2;
location / {
root html;
index index.html index.htm;
}
}
}Теперь мы можем использовать настроенные LDAP‑серверы для аутентификации в рамках сервера:
server {
listen 8000;
server_name localhost;
auth_ldap "Forbidden";
auth_ldap_servers test1;
auth_ldap_servers test2;
location / {
root html;
index index.html index.htm;
}
}В примере выше мы активируем LDAP‑модуль с помощью директивы auth_ldap и задаем серверы для аутентификации директивами auth_ldap_servers. К сожалению, документация на странице проекта модуля довольно скупая.
Модуль Auth PAM
Для аутентификации в Angie можно использовать стандартные возможности модульной системы PAM в Linux. Для этого используем сторонний модуль Auth PAM. Установка модуля доступна из репозитория Angie:
apt|dnf install angie-module-auth-pamПодключаем модуль в главном (main) контексте:
load_module modules/ngx_http_auth_pam_module.so;Теперь нам доступны дополнительные директивы; полное описание модуля см. в документации. Например, через PAM можно настроить аутентификацию с помощью LDAP. Мы же настроим простую аутентификацию с использованием локальных пользователей системы в Linux. Предполагается использование ОС Ubuntu 24.04, поэтому для других систем в конфигурации возможны отличия. Создаём конфиг для PAM (/etc/pam.d/angie) с таким содержимым:
auth required pam_unix.so
account required pam_unix.soЗдесь мы привязываем аутентификацию к проверке логина и пароля пользователя в файлах /etc/passwd и /etc/shadow. Так как сервер работает с обычным пользователям (в нашем случае www‑data), то по умолчанию у него нет доступа к файлу /etc/shadow:
ls -al /etc/shadow
-rw-r----- 1 root shadow 1167 Sep 4 12:53 /etc/shadowЧтобы разрешить доступ, достаточно добавить пользователя сервера в группу shadow:
usermod -aG shadow www-dataНа этом подготовка системы завершена. Осталось настроить локацию с аутентификацией через PAM:
location /secure/ {
auth_pam "Secure Zone";
auth_pam_service_name "angie";
}Директива auth_pam включает аутентификацию через модуль Auth PAM, а auth_pam_service_name указывает на имя сервиса (конфига в pam.d). Если всё настроено корректно, то при доступе к этой локации мы получим приглашение для ввода пользователя и пароля — можно указать локального пользователя и получить доступ. Учитывайте при тестировании, что успешная аутентификация кэшируется в браузере, поэтому проверку изменений стоит производить в инкогнито‑режиме.
Итоги
Мы разобрали различные варианты решения задачи контроля доступа с помощью аутентификации в веб‑сервере Angie. Набор возможностей довольно широк: от базовой аутентификации с помощью встроенных модулей до интеграции с LDAP и Kerberos с применением сторонних модулей. Также мы слегка затронули тему расширениях функциональности сервера с помощью модуля NJS, который также можно применять для задач аутентификации.