Директива Nginx proxy_set_header позволяет изменять или добавлять заголовки HTTP при пересылке запросов на внутренние серверы. Она обеспечивает гибкий способ управления и настройки заголовков, отправляемых с сервера Nginx на вышестоящие серверы. В этом руководстве мы рассмотрим proxy_set_header. Мы обсудим ее назначение, использование и различные способы ее настройки для управления заголовками HTTP. Независимо от того, являетесь ли вы новичком в Nginx или опытным пользователем, понимание директивы proxy_set_header позволит вам улучшить функциональность вашего веб-сервера и улучшить связь между Nginx и внутренними серверами.

Что означает proxy_set_header host $host?

Одним из наиболее распространенных вариантов использования директивы proxy_set_header является изменение заголовка Host. Заголовок Host указывает доменное имя или IP-адрес сервера, к которому клиент делает запрос. Конфигурация proxy_set_header host $host; устанавливает заголовок Host в пересылаемом запросе на то же значение, что и заголовок Host исходного запроса.

Настройка заголовков с помощью proxy_set_header

Если вы еще не настроили Nginx в качестве обратного прокси на своем сервере, мы рекомендуем обратиться к нашей комплексной статье, которая содержит пошаговое руководство. Она охватывает весь процесс настройки Nginx в качестве обратного прокси, гарантируя вам прочную основу, прежде чем двигаться дальше.

Вот пример конфигурации, демонстрирующий использование директивы proxy_set_header Nginx, которую мы объясним в этом руководстве.

server {
    listen 80;
    server_name example.com;

    location/{
        proxy_pass http://backend;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_pass_request_headers on;
        proxy_hide_header X-Powered-By;
        proxy_set_header_if_empty X-Custom-Header "Default Value";
        proxy_set_header Strict-Transport-Security $http_strict_transport_security;
        proxy_set_header Content-Security-Policy $http_content_security_policy;
    }

    location /api {
        proxy_pass http://backend;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Custom-Header1 "Value1";
        proxy_set_header X-Custom-Header2 "Value2";
        proxy_hide_header X-Powered-By;
        proxy_set_header_if_empty X-Custom-Header "Default Value";
        proxy_set_header Strict-Transport-Security $http_strict_transport_security;
        proxy_set_header Content-Security-Policy $http_content_security_policy;
    }
}

Обратите внимание, что вам может потребоваться настроить имя сервера (example.com) и директиву proxy_pass в соответствии с настройками вашего сервера. Кроме того, убедитесь, что необходимые модули включены и все другие конфигурации, специфичные для сервера, находятся на месте.

Обязательно протестируйте и проверьте конфигурацию на вашем рабочем сервере перед ее развертыванием. Теперь давайте разберем эту конфигурацию:

Начиная с настройки заголовков с помощью директивы proxy_set_header, можно использовать следующий синтаксис:

proxy_set_header header_name value;

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

location /api {
    proxy_pass http://backend;
    proxy_set_header X-Forwarded-For $remote_addr;
    proxy_set_header User-Agent $http_user_agent;
}

В приведенной выше конфигурации директива proxy_set_header используется для установки заголовка X-Forwarded-For на IP-адрес клиента ($remote_addr), а заголовка User-Agent — на значение заголовка User-Agent исходного запроса ($http_user_agent).

Анатомия директивы Nginx proxy_set_header

Директива Nginx proxy_set_header состоит из двух частей: имени заголовка и его значения. Вы можете задать имя заголовка для любого допустимого имени поля заголовка HTTP. Значение может быть статической строкой или может включать переменные, представляющие динамические значения.

Например:

proxy_set_header X-Custom-Header "Hello, World!";

Здесь для каждого пересылаемого запроса X-Custom-Header будет установлена ​​статическая строка "Hello, World!".

Определение пользовательских заголовков в Nginx

Помимо изменения существующих заголовков, вы также можете определить пользовательские заголовки с помощью директивы proxy_set_header. Пользовательские заголовки позволяют отправлять дополнительную информацию на внутренние серверы или выполнять определенные действия на основе этих заголовков.

Рассмотрим следующий пример:

location /api {
    proxy_pass http://backend;
    proxy_set_header X-Custom-Header1 "Value1";
    proxy_set_header X-Custom-Header2 "Value2";
}

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

Сохранение исходных заголовков клиента

При проксировании запросов на серверы верхнего уровня часто желательно сохранять исходные заголовки клиента. Это гарантирует, что сервер верхнего уровня получит те же заголовки, что и исходный клиентский запрос. Директива proxy_set_header Nginx может использоваться для сохранения определенных заголовков или передачи всех заголовков на сервер верхнего уровня.

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

proxy_set_header header_name $http_header_name;

Например, чтобы сохранить заголовок Accept-Language:

location /api {
    proxy_pass http://backend;
    proxy_set_header Accept-Language $http_accept_language;
}

В приведенной выше конфигурации заголовок Accept-Language исходного клиентского запроса передается на вышестоящий сервер.

Чтобы передать все заголовки из клиентского запроса, можно использовать директиву proxy_pass_request_headers в сочетании с proxy_set_header:

location /api {
    proxy_pass http://backend;
    proxy_pass_request_headers on;
}

При такой конфигурации все заголовки клиентского запроса будут переданы на вышестоящий сервер.

Изменение заголовков для восходящих запросов

Директива proxy_set_header также может быть использована для изменения заголовков для upstream-запросов. Это позволяет вам настраивать заголовки, отправляемые из Nginx на upstream-сервер.

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

location /api {
    proxy_pass http://backend;
    proxy_set_header X-Request-ID $request_id;
}

В этом случае заголовок X-Request-ID устанавливается в значение переменной $request_id, которая может быть уникальным идентификатором, сгенерированным Nginx или извлеченным из заголовка запроса.

Управление поведением заголовков в Nginx

Nginx предоставляет дополнительные директивы для управления поведением заголовков. Две важные директивы — это proxy_hide_header и proxy_set_header_if_empty.

Директива Nginx позволяет proxy_hide_header удалять определенные заголовки из ответа, отправленного вышестоящим сервером. Например:

location /api {
    proxy_pass http://backend;
    proxy_hide_header X-Powered-By;
}

Вышеуказанный заголовок X-Powered-By будет удален из ответа перед его отправкой клиенту.

Директива Nginx позволяет proxy_set_header_if_empty вам задать заголовок, только если он не существует в ответе upstream. Это полезно, когда вы хотите добавить значение по умолчанию для заголовка, если его еще нет. Вот пример:

location /api {
    proxy_pass http://backend;
    proxy_set_header_if_empty X-Custom-Header "Default Value";
}

В этой конфигурации значение X-Custom-Header будет установлено "Default Value" только в том случае, если оно еще не присутствует в ответе восходящего потока.

Обработка заголовков безопасности и конфиденциальности

При проксировании запросов важно правильно обрабатывать заголовки безопасности и конфиденциальности. Например, вы можете захотеть убедиться, что такие конфиденциальные заголовки, как Strict-Transport-Security или Content-Security-Policy передаются клиенту правильно.

Для обработки заголовков безопасности можно использовать директиву proxy_set_header nginx, как показано в следующем примере:

location/{
    proxy_pass http://backend;
    proxy_set_header Strict-Transport-Security $http_strict_transport_security;
    proxy_set_header Content-Security-Policy $http_content_security_policy;
}

В этой конфигурации заголовки Strict-Transport-Security и Content-Security-Policy передаются от вышестоящего сервера клиенту, сохраняя их значения.

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

Заключение

Поздравляем! Вы узнали о директиве proxy_set_header Nginx и о том, как она может улучшить функциональность вашего веб-сервера. Используя эту директиву, вы можете изменять или добавлять заголовки HTTP при пересылке запросов на внутренние серверы, что обеспечивает больший контроль и настройку. Независимо от того, новичок ли вы в Nginx или опытный пользователь, понимание директивы proxy_set_header Nginx позволит вам оптимизировать связь между Nginx и вашими внутренними серверами.

Помните, что изменение заголовка Host с помощью является proxy_set_header распространенным вариантом использования. Эта директива позволяет вам гарантировать, что заголовок Host в пересылаемом запросе соответствует исходному запросу, поддерживая точную маршрутизацию.

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

Written by Иван Васильков

Системный администратор и DevOps с опытом 10+ лет.