ßàØÃÂâÕàë áÕÓÞÔÃÂï - Xakep Online
ßàØÃÂâÕàë áÕÓÞÔÃÂï - Xakep Online
ßàØÃÂâÕàë áÕÓÞÔÃÂï - Xakep Online
You also want an ePaper? Increase the reach of your titles
YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.
ХАКЕР 04/ /171/ 2013 Новые горизонты133ПОЧТОВЫЙ ПРОКСИНачнем с самого очевидного — со способности nginx выступать в роли почтовогопрокси. Эта функция есть в nginx изначально, а вот используетсяв продакшн она почему-то крайне редко, некоторые так и вообще не догадываютсяо ее существовании. Как бы там ни было, nginx поддерживает проксированиепротоколов POP3, IMAP и SMTP с разными методами аутентификации,включая SSL и StartTLS, причем делает это очень быстро.Зачем это нужно? Есть как минимум два применения данной функциональности.Первая: использовать nginx в качестве щита от назойливых спамеров,пытающихся отправить мусорные письма через наш SMTP-сервер.Обычно спамеры не создают много проблем, так как быстро отшибаютсяна этапе аутентификации, однако, когда их становится действительно много,nginx поможет сэкономить процессорные ресурсы. Вторая: использоватьnginx для перенаправления пользователей на несколько почтовых POP3/IMAP-серверов. С этим, конечно, мог бы справиться и другой почтовый прокси,но зачем городить огород серверов, если на фронтенде уже установленnginx для отдачи статики по HTTP, например?Почтовый прокси-сервер в nginx сделан не совсем стандартно. Он используетдополнительный слой аутентификации, реализованный средствамиHTTP, и, только если пользователь проходит этот барьер, он пропускаетсядальше. Обеспечивается такая функциональность путем создания страницы/скрипта,которой nginx отдает данные пользователя, а она/он возвращаетответ в виде стандартных OK или причины отказа (типа «Invalid login orpassword»). Скрипт запускается со следующими заголовками:Входные данные скрипта аутентификацииHTTP_AUTH_USER: юзерHTTP_AUTH_PASS: парольHTTP_AUTH_PROTOCOL: почтовый протокол (IMAP, POP3 или SMTP)А возвращает такие:Выходные данные скрипта аутентификацииHTTP_AUTH_STATUS: OK или причина отказаHTTP_AUTH_SERVER: реальный почтовый сервердля перенаправленияHTTP_AUTH_PORT: порт сервераЗамечательная особенность такого подхода в том, что его можно использоватьвовсе не для самой аутентификации, а чтобы раскидать пользователейпо разным внутренним серверам, в зависимости от имени юзера,данных о текущих нагрузках на почтовые серверы либо вообще организовавпростейшую балансировку нагрузки с помощью round-robin. Впрочем, еслитребуется всего лишь перекинуть пользователей на внутренний почтовыйсервер, можно использовать вместо реального скрипта заглушку, реализованнуюсамим nginx. Например, простейший SMTP- и IMAP-прокси в конфигеnginx будет выглядеть следующим образом:# vi /etc/nginx/nginx.confmail {# Адрес скрипта аутентификацииauth_http localhost:8080/auth;# Отключаем команду XCLIENT, некоторые почтовые# серверы ее не понимаютxclient off;# IMAP-серверserver {listen 143;protocol imap;proxy on;}# SMTP-серверserver {listen 25;protocol smtp;proxy on;}}Далее в секцию http конфига добавляем следующее:# vi /etc/nginx/nginx.confhttp {# Маппинг на нужный порт почтового сервера# в зависимости от порта, отправленного в заголовке# HTTP_AUTH_PROTOCOLmap $http_auth_protocol $mailport {Тестирование производительности с выключенным/включенныммикрокешированием}}default 25;smtp 25;imap 143;# Реализация «скрипта» аутентификации — всегда# возвращает OK и перекидывает пользователя# на внутренний почтовый сервер, выставляя нужный# порт с помощью приведенного выше маппингаserver {listen 8080;location /auth {add_header "Auth-Status" "OK";add_header "Auth-Server" "192.168.0.1";add_header "Auth-Port" $mailport;return 200;}}Это все. Такая конфигурация позволяет прозрачно перенаправлять пользователейна внутренний почтовый сервер, не создавая оверхеда в виде ненужногов данном случае скрипта. Применив скрипт, такую конфигурациюможно существенно расширить: настроить балансировку нагрузки, проверятьпользователей по базе LDAP и выполнять другие операции. Написаниескрипта выходит за рамки этой статьи, однако его очень легко реализовать,даже имея лишь поверхностные знания о PHP и Python.Зачем городить огород серверов,если на фронтенде уже установленnginx для отдачи статики по HTTP?