Обнаружение HTTPS и HTTP на сервере, не отправляющем ничего полезного

Очень похоже на "Обнаружение https-запросов в php< /а>":

Хотите иметь https://example.com/pog.php, перейдите на http://example.com/pog.php или даже наоборот.

Проблемы:

  • Не могу ничего прочитать из $_SERVER["HTTPS"], так как его там нет
  • Сервер отправляет оба запроса через порт 80, поэтому не может проверить 443 в версии HTTPS.
  • apache_request_headers() и apache_response_headers() возвращают одно и то же
  • Не могу ничего сказать балансировщику нагрузки или отправить что-то лишнее
  • Данные обратной связи сервера, выдаваемые страницей при обоих вызовах URL, точно такие же, за исключением идентификатора сеанса. облом.

Есть ли на странице способы определить, вызывается ли она через SSL или без SSL?

Изменить: $_SERVER["HTTPS"] там нет, включен он или нет, независимо от того, просматриваете ли вы сайт через SSL или без него. По какой-то причине хостинг решил обслуживать все HTTPS-запросы в зашифрованном виде, но не на 80-м порту. И, таким образом, $_SERVER["HTTPS"] никогда не включен, не там, просто нет полезной обратной связи по этому серверу. Так что этот параметр всегда должен быть пустым.

(И да, это означает, что он помечен, скажем, в FF или Chrome для частично недействительного SSL-сертификата. Но эта часть не имеет значения.)

Кроме того, максимум, что можно получить от определения URL-адреса, — это косая черта. PHP не может видеть, есть ли в запросе https или http впереди.


person random    schedule 16.02.2009    source источник


Ответы (2)


Ключевое слово – балансировщик нагрузки

Проблема сводится к тому, что балансировщик нагрузки обрабатывает SSL-шифрование/дешифрование и полностью прозрачен для веб-сервера.

Request:  Client -> 443or80 -> loadbalancer -> 80 -> php
Response: PHP -> 80 -> loadbalancer -> 443or80 -> Client

Настоящий вопрос здесь заключается в том, "есть ли у вас контроль над конфигурацией балансировщика нагрузки?"


Если да, есть несколько способов справиться с этим. Настройте балансировщик нагрузки, чтобы он имел отдельные определения служб для HTTP и HTTPS. Затем отправьте трафик HTTP на порт 80 веб-серверов и трафик HTTPS на порт 81 веб-серверов. (порт 81 больше ничем не занят).

В apache настройте два разных виртуальных хоста:

<VirtualHost 1.2.3.4:80>
   ServerName foo.com
   SetEnv USING_HTTPS 0
   ...
</VirtualHost>

<VirtualHost 1.2.3.4:81>
   ServerName foo.com
   SetEnv USING_HTTPS 1
   ...
</VirtualHost>

Затем переменная окружения USING_HTTPS будет либо 1|0, в зависимости от того, какой виртуальный хост ее выбрал. Это будет доступно в массиве $_SERVER в PHP. Разве это не круто?


Если у вас нет доступа к конфигурации Load Balancer, все немного сложнее. Невозможно точно узнать, используете ли вы HTTP или HTTPS, поскольку HTTP и HTTPS являются протоколами. Они указывают, как подключиться и в каком формате отправлять информацию, но в любом случае вы используете HTTP 1.1 для выполнения запроса. В фактическом запросе нет информации, чтобы сказать, является ли он HTTP или HTTPS.

Но не падайте духом. Есть пара идей.

Шестой параметр PHP-функции setcookie() может указать клиенту отправлять cookie ТОЛЬКО через соединения HTTPS (http://www.php.net/setcookie). Возможно, вы могли бы установить cookie с этим параметром, а затем проверять его при последующих запросах?

Другой возможностью было бы использование JavaScript для обновления ссылок на каждой странице в зависимости от протокола (добавление параметра GET).

(ни один из вышеперечисленных вариантов не является пуленепробиваемым)

Другим прагматичным вариантом было бы получить ваш SSL в другом домене, таком как secure.foo.com. Тогда вы можете прибегнуть к трюку VirtualHost, описанному выше.


Я знаю, что это не самая простая проблема, потому что я занимаюсь ею в течение дня (веб-кластер с балансировкой нагрузки за балансировщиком нагрузки Cisco CSS с модулем SSL).

Наконец, вы всегда можете принять точку зрения, что ваше веб-приложение должно переключаться в режим SSL, когда это необходимо, и доверять пользователям, которые НЕ вернут его обратно (в конце концов, это их данные на линии (обычно)).

Надеюсь, это немного поможет.

person gahooa    schedule 16.02.2009
comment
Никогда не доверяйте пользователю. Страница должна оставаться на HTTP-версии, поэтому, если они когда-либо попытаются перейти на HTTPS, они вернутся к HTTP-версии. Хотя твой ответ понравился. - person random; 16.02.2009

$_SERVER["HTTPS"] isn't there, switched on or not, no matter if you're looking at the site via SSL or non-SSL. For some reason the hosting has chosen to serve all the HTTPS requests encrypted, but down port 80. And thusly, the $_SERVER["HTTPS"] is never on, not there, just no helpful feedback on that server point. So that parameter is always be empty.

Вы должны убедиться, что у провайдера есть следующая строка в записи VHOST для вашего сайта: SSLOptions +StdEnvVars. Эта строка указывает Apache включить переменные SSL в среду для ваших скриптов (PHP).

person nabrond    schedule 17.02.2009