Рейтинг:0

nginx proxy_pass для данного пользовательского агента

флаг cn

У меня есть веб-сайт с nginx, который возвращает index.html (одностраничное приложение для реагирования) почти для всех запросов.Любой запрос практически для любого пути (например, /некоторые/статья) тоже вернется index.html, и приложение реакции (маршрутизатор реакции) преобразует путь в вызовы API. Вот как это работает, и это нельзя изменить (веб-сайт огромен, это слишком много работы, и я все равно не в состоянии это изменить).

Для этих запросов должно быть два исключения:

  1. Все запросы, начинающиеся с пути /api/*, передаются вышестоящему серверу (серверу приложений). Таким образом, другой бэкэнд будет обрабатывать все фактические запросы API.
  2. Другим исключением должны быть внешние хиты Facebook. Для этого существует другая конечная точка в /api/open_graph на сервере приложений. Например. /api/open_graph должен быть указан перед исходным путем. Эта конечная точка возвращает фактический контент (а не обычное одностраничное приложение, которое не имеет реального контента). Формат также отличается — обычные вызовы API обычно возвращают данные JSON, а конечная точка open_graph возвращает простой HTML.

Пример конфигурации nginx:

вверх по течению www {
    # ...
}

сервер {
    # ...

    # Используйте /api/open_graph в апстриме для внешних обращений в Facebook
    если ($http_user_agent ~* "^facebookexternalhit.*$") {
        переписать ^/(.*)$ /api/open_graph/$1 навсегда;
    }

    # API-запросы будут отправляться вверх по течению
    расположение ~ ^/api/ {
        прокси_пароль http://www;
        proxy_read_timeout 90;
        proxy_redirect http://www https://example.com;
    }

    # Все остальные запросы используют реагирующее приложение,
    # react router обрабатывает все дальнейшие запросы
    место расположения / {
        индекс index.html;
        error_page 404 = 200 /index.html;
    }

}

Приведенный выше конфиг работает следующим образом:

# curl -A "facebookexternalhit" -s -D - -o /dev/null https://example.com/article1
HTTP/1.1 301 перемещен навсегда
Сервер: nginx
Дата: среда, 20 октября 2021 г., 08:14:13 по Гринвичу
Тип содержимого: текст/html
Длина содержимого: 162
Расположение: https://example.com/api/open_graph/article1.
Соединение: Keep-alive
Строгая транспортная безопасность: max-age=31536000
X-Content-Type-Options: nosniff
X-XSS-защита: 1; режим = блок
Параметры X-Frame: SAMEORIGIN

Это почти хорошо, за исключением того, что api facebook graph не обрабатывает перенаправления. (Кто знает почему?). Поэтому вместо перенаправления на /апи/open_graph/* сервер должен напрямую подключаться к восходящему потоку и пересылать запрос.

Но я не знаю как? Наивным решением было бы:

    # Используйте /api/open_graph в апстриме для внешних обращений в Facebook
    если ($http_user_agent ~* "^facebookexternalhit.*$") {
        переписать ^/(.*)$ /api/open_graph/$1 навсегда;
        прокси_пароль http://www;
        proxy_read_timeout 90;
        proxy_redirect http://www https://example.com;
    }

Но это не работает, потому что proxy_pass можно использовать только внутри место расположения. Его нельзя использовать внутри если. Если я попробую эту конфигурацию, я получу:

nginx: [появление] директива proxy_pass не разрешена здесь, в /etc/nginx/sites-enabled/example-www:62
nginx: проверка файла конфигурации /etc/nginx/nginx.conf не удалась

Я мог бы изменить код программы в восходящем потоке (например, добавить туда фильтр для пользовательского агента), но это было бы довольно сложно.

Есть ли обходной путь для этого в nginx?

Этот вопрос связан с: nginx — proxy_pass на user_agent но у меня это тоже не сработало (выдало ошибку)

Richard Smith avatar
флаг jp
Попробуйте изменить исходную конфигурацию с «постоянной» на «последнюю».
Egidijus avatar
флаг nz
При скручивании в dev попробуйте эти флаги, чтобы обойти самоподписанные сертификаты, следуйте перенаправлениям и получите больше пользы: `curl -ivLk https://yahoo.com`

Ответить или комментировать

Большинство людей не понимают, что склонность к познанию нового открывает путь к обучению и улучшает межличностные связи. В исследованиях Элисон, например, хотя люди могли точно вспомнить, сколько вопросов было задано в их разговорах, они не чувствовали интуитивно связи между вопросами и симпатиями. В четырех исследованиях, в которых участники сами участвовали в разговорах или читали стенограммы чужих разговоров, люди, как правило, не осознавали, что задаваемый вопрос повлияет — или повлиял — на уровень дружбы между собеседниками.