Назад | Перейти на главную страницу

Изменяйте данные, проксируемые nginx на лету

У меня есть настройка nginx, которая получает запросы от внешних хостов и передает их на внутренний сервер.

Конфигурация выглядит примерно так:

server {

        listen 10.0.0.66:443;

        server_name my.example.com;

        root /websites/my.example.com

        ssl on;
        ssl_certificate /websites/ssl/my.example.com.crt;
        ssl_certificate /websites/ssl/my.example.com.key;

        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $remote_addr;
        proxy_set_header Host $http_host;

        location / {
                proxy_pass https://10.0.0.100:3000/;
        }
}

В экспериментальных / тестовых целях я хотел бы иметь возможность запускать то, что внутренний хост ответил через произвольный двоичный файл, и отвечать тем, чем отвечает двоичный файл.

Для пример, если бы я хотел минимизировать html на прокси-сервере, я бы запустил ответ сервера через htmlcompressor, а затем отправил бы вывод в качестве ответа прокси-сервера клиенту. Конечным результатом будет возвращение конечному клиенту минимизированного HTML.

Я знаю, что для nginx есть всевозможные надстройки и примеры для выполнения этого для локально обслуживаемых данных, но как настроить его для прокси?

Итак, вы хотите nginx проксировать запрос от клиента к внутреннему серверу, а затем, прежде чем возвращать ответ серверной части клиенту, направить такой ответ через другой внешний процессор?

Я не думаю, что вы сможете сделать это с любым официальным лицом nginx модули, предоставленные Игорем Сысоевым и Nginx, Inc. Ближайшее, что доступно для изменения тела ответа, - это несколько модулей фильтров, которые идут вместе с nginx, но по умолчанию отключены, включая add_before_body, add_after_body и sub_filter директивы:

http://nginx.org/en/docs/http/ngx_http_addition_module.html
http://nginx.org/en/docs/http/ngx_http_sub_module.html

Также, возможно gzip on; это то, что вы действительно хотите вместо этого?

http://nginx.org/en/docs/http/ngx_http_gzip_module.html

Или, возможно, если вы знаете perl и готовы запустить полностью экспериментальный модуль, обратите внимание на встраивание perl в nginx, с официальным модулем nginx, который по умолчанию отключен и является (несколько очевидно) полностью экспериментальным:

http://nginx.org/en/docs/http/ngx_http_perl_module.html

Другой вариант - использовать какую-то настройку Fast-CGI, на которую вы будете перенаправлять запросы, где, в свою очередь, ваш сценарий Fast-CGI будет выполнять запросы к бэкэнду, а затем заключительную обработку перед возвратом. ответы обратно в nginx для кеширования и возврата пользователю.

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

(Кроме того, вы понимаете, что наивный подход forkПолучение и передача ответов через обычного руководителя будет очень медленным, не так ли?)

Чтобы обобщить, Думаю gzip on; это именно то, что вы ищете; в противном случае, при условии, что вы можете изменить исходное веб-приложение, я думаю, что лучше всего будет установить какой-то постпроцессор внутри самого веб-приложения, что может показаться следующим самым простым решением в целом. Возможно, вы могли бы изучить, как модули фильтров реализованы, например вышеупомянутый ngx_http_addition_filter_module.c, плюс несколько более очевидных релевантных фильтров, таких как ngx_http_gzip_filter_module.c, и реализовать собственный встроенный модуль фильтра. Или наймите Nginx, Inc., чтобы написать это за вас! Но серьезно, gzip on; просто работает и, вероятно, даст вам гораздо лучшие результаты без каких-либо проблем, проблем с производительностью или стабильностью, и он уже скомпилирован по умолчанию, вам просто нужно включить его в nginx.conf.

Я думаю, если вы хотите запустить произвольный код для изменения вывода nginx, ... вы можете написать lua-скрипт.

Найдите "nginx lua".

(Пример: http://www.londonlua.org/scripting_nginx_with_lua/slides.html?full#hello-lua)