Получить полный URL и строку запроса в Servlet для HTTP и HTTPS-запросов

Я пишу код, задачей которого является получение запрошенного URL-адреса или полного пути. Я написал этот код:

HttpServletRequest request;//obtained from other functions String uri = request.getRequestURI(); if (request.getQueryString() != null) uri += "?" + request.getQueryString(); 

Поэтому, когда я просматриваю http://google.com?q=abc это нормально (правильно). Но есть проблема, когда я просматриваю https://google.com . Значение urihttp://google.com:443google.com:443 , поэтому программа используется не только при использовании HTTPS .

Результат такой же для request.getRequestURL().toString() .

Каково решение?

По дизайну getRequestURL() дает вам полный URL-адрес, не getRequestURL() только строку запроса.

В HttpServletRequest вы можете получить отдельные части URI, используя следующие методы:

 // Example: http://myhost:8080/people?lastname=Fox&age=30 String uri = request.getScheme() + "://" + // "http" + ":// request.getServerName() + // "myhost" ":" + // ":" request.getServerPort() + // "8080" request.getRequestURI() + // "/people" "?" + // "?" request.getQueryString(); // "lastname=Fox&age=30" 
  • .getScheme() даст вам "https" если это запрос https://domain .
  • .getServerName() предоставляет domain в http(s)://domain .
  • .getServerPort() предоставит вам порт.

Используйте нижеприведенный fragment:

 String uri = request.getScheme() + "://" + request.getServerName() + ("http".equals(request.getScheme()) && request.getServerPort() == 80 || "https".equals(request.getScheme()) && request.getServerPort() == 443 ? "" : ":" + request.getServerPort() ) + request.getRequestURI() + (request.getQueryString() != null ? "?" + request.getQueryString() : ""); 

Этот fragment выше получит полный URI, скрывая порт, если используется по умолчанию, и не добавляя "?" и строку запроса, если последняя не была предоставлена.

Прокси-запросы

Обратите внимание, что если ваш запрос проходит через прокси-сервер, вам нужно посмотреть заголовок X-Forwarded-Proto поскольку схема может быть изменена:

 request.getHeader("X-Forwarded-Proto") 

Кроме того, общий заголовок X-Forwarded-For , который показывает исходный IP-адрес запроса вместо proxys-IP.

 request.getHeader("X-Forwarded-For") 

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

Простое использование:

 String Uri = request.getRequestURL()+"?"+request.getQueryString(); 

Тот факт, что запрос HTTPS становится HTTP когда вы пытались построить URL-адрес на стороне сервера, указывает на то, что у вас может быть балансировщик прокси / нагрузки ( nginx , pound и т. Д.), Разгружая SSL-шифрование спереди и вперед к вашей задней службе на простом HTTP .

Если это так, проверьте,

  1. был ли ваш прокси настроен правильно направить заголовки ( Host , X-forwarded-proto , X-forwarded-for и т. д.).
  2. установлен ли ваш контейнер обслуживания (например, Tomcat ) для распознавания прокси-сервера спереди. Например, Tomcat требует добавить к своему Connector атрибуты secure="true" scheme="https" proxyPort="443"
  3. независимо от того, обрабатывает ли ваш код или контейнер обслуживания правильные заголовки. Например, Tomcat автоматически заменяет значения scheme , remoteAddr и т. Д., Когда вы добавляете RemoteIpValve в свой Engine . (см. Руководство по настройке , JavaDoc ), поэтому вам не нужно обрабатывать эти заголовки в коде вручную.

Неправильные значения заголовка прокси могут приводить к некорректному выводу, когда request.getRequestURI() или request.getRequestURL() пытается request.getRequestURL() исходный URL-адрес.

  • Как правильно декодировать параметры юникода, переданные в сервлет
  • Разделение общего кода и web.xml из проекта WAR в общий проект JAR
  • Java Front Controller
  • Метод getDispatcherType () не определен для типа HttpServletRequest
  • Получение запроса полезной нагрузки из запроса POST в Java-сервлете
  • Как реализовать разбиение на страницы весной MVC 3
  • Как загрузить ресурс из файла jar, упакованного в военный файл?
  • Как решить этот java.lang.NoClassDefFoundError: org / apache / commons / io / output / DeferredFileOutputStream?
  • Модуль тестирования сервлетов Java
  • Доступ к пост-переменным с использованием сервлетов Java
  • Браузер не может получать / находить относительные ресурсы, такие как CSS, изображения и ссылки при вызове сервлета, который пересылает JSP
  • Давайте будем гением компьютера.