Обратный прокси на Nginx

Обратный прокси на Nginx 01Обратный прокси на Nginx может оказаться очень полезным компонентом вашей инфраструктуры веб-сервисов, позволяя горизонтально масштабировать ресурсы между множеством серверов или виртуальных машин. С его помощью разные ресурсы (например blog.site.tld и forum.site.tld) можно разместить на разных экземплярах ОС.


Если вам интересна тематика Debian и связанных с ним приложений, рекомендую обратиться к тегу Debian на моем блоге


Обратный прокси на Nginx

Чтение статей не избавляет вас от ответственности ознакомления с официальной 1 документацией! Также рекомендую обратиться к книге Администрирование сервера NGINX, из которой я почерпнул для себя множество нюансов, частично описанных в этой статье. Итак, начнем.

Балансировщик layer 7

Если в статье Простейший отказоустойчивый балансировщик layer 4 шла речь о балансировке на уровне tcp-соединений, то в этот раз я хочу рассказать про балансировку 7 уровня, на котором происходит анализ заголовков протоколов более высокого уровня (в частности http).

Подготовка

Сделаем бэкап основного конфига Nginx (всегда рекомендую начинать именно с этого):

Перенесем актуальные строчки конфигурации из бэкапа в основной nginx.conf:

Примечание: шаблон поиска может показаться сложным, но на деле он легко расщепляется на две секции — -e /^[^#]/!d и -e /^[[:space:]]*#.*$/d. В первой секции будут удалены все строчки, имеющие первый символ # (а также пустые строки), во втором случае удалятся все строки, в которых первым/и символами будут пробелы, а после них #. Конструкция с объединением двух команд в одну актуальна для GNU sed; в POSIX sed этот вариант не поддерживается и необходимо явно разделять шаблоны поиска ключами -e.

Итоговый дефолтный конфиг для версии nginx 1.10.3:

Можно переходить к дальнейшей настройке.

Базовая конфигурация

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

Не забываем перезапустить демона командой:

Или:

Полная конфигурация:

Выше я прописал лишь явно необходимые опции и опустил необязательные. Например nginx по умолчанию прослушивает порт 80, но это можно и не упоминать. Если нужно слушать на другом порту, вы можете задать опцию внутри секции server вот так:

По умолчанию используется режим балансировки round-robin, но вы можете выбрать другой и прописать его в секции upstream:

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

Пришло время рассмотреть более разнообразные варианты.

Разные URL для одного домена

Может возникнуть ситуация, когда разные адреса нужно обрабатывать по-разному. Например при отдаче статического контента отправлять пользователей на один бэкэнд, а при запросе динамических данных — на другой. При этом никто вам не запрещает иметь несколько бэкэндов.

Вот как это может выглядеть:

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

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

Регулярные выражения

Дабы избежать излишнее размножение местоположений, рекомендуется использовать регулярные выражения 2 3. Разумеется, где это возможно:

Примечание: будьте внимательны — если местоположение (location) определено с помощью регулярного выражения, преобразование URL выполняться не будет. То есть, если бы директива proxy_pass в примере выше имела значение, например, http://old_blog/archive_data, то при обращении к /old или к /archive, преобразование URL в /archive_data не призошло бы.

Стоит отметить, что nginx будет выбирать вариант с наиболее точным соответствием.

Несколько доменов

Один из распространенных вариантов конфигурации — необходимость обработки нескольких доменных имен. В зависимости от того или иного имени может понадобиться разная логика обработки.

Примечание: для решения этой задачи, вероятно, у вас также возникнет желание использовать условный оператор if. Тем не менее, эту задачу также лучше решить по-другому, ведь конструкция с if будет смотреться более громоздкой и сложной для понимания, не давая при этом никаких преимуществ в производительности, а даже наоборот.

Вот так может выглядеть ваша конфигурация:

На этом базовой информации для быстрого старта должно быть достаточно.1

comments powered by HyperComments