1. ホーム
  2. java

[解決済み] HTTPとHTTPSの両方のリクエストに対して、Servletで完全なURLとクエリ文字列を取得する。

2023-08-25 03:47:47

質問

私はタスクが要求されたURLまたはフルパスを取得することであるコードを書いています。私はこのコードを書きました。

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

で、ブラウズすると http://google.com?q=abc を参照すると、OK(正しい)です。 しかし https://google.com . の値が urihttp://google.com:443google.com:443 である場合のみ、プログラムは HTTPS が使われているときだけです。

また、出力は request.getRequestURL().toString() .

解決策は何ですか?

どのように解決するのですか?

デザインで getRequestURL() は、クエリ文字列だけが欠けた完全な URL を提供します。

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() 与える domainhttp(s)://domain .
  • .getServerPort() を実行すると、ポートが表示されます。

以下のスニペットを使用します。

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() : "");

上記のスニペットは、完全な URI を取得し、デフォルトのポートが使用されている場合はポートを隠し、さらに "?" とクエリ文字列が提供されていない場合は追加しません。



プロキシされたリクエスト

リクエストがプロキシを通過する場合、プロキシを通過する前に X-Forwarded-Proto ヘッダを見る必要があることに注意してください。

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

また、一般的なヘッダは X-Forwarded-For で、これはプロキシの IP ではなく、オリジナルのリクエストの IP を表示します。

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

プロキシ/ロードバランサの設定を自分で行う場合、転送時にこれらのヘッダが設定されていることを確認する必要があります。