プロキシ経由でHTTP接続(Proxy認証)


認証が必要なプロキシ経由で、HTTP接続をする方法です。
Apache Jakarta Project CommonsHttpClient を使用します。

準備

HttpClient のダウンロード

Apache Jakarta Project CommonsHttpClient サイトの Download から、アーカイブをダウンロードします。
HttpClient のダウンロード


依存モジュールのダウンロード

HttpClientを使用するには、Apache Jakarta Project Commonscommons-codeccommons-logging が必要です。それぞれダウンロードします。

commons-codec
commons-codecのダウンロード
commons-codecのダウンロード

commons-logging
commons-loggingのダウンロード
commons-loggingのダウンロード

配置

それそれのアーカイブから jar ファイルを展開します。
commons-httpclient-3.0.1.jar
commons-codec-1.3.jar
commons-logging-1.1.jar

クラスパスが通っている場所に配置するか、実行時に 各jar ファイルをクラスパスに指定します。


実装

実装の流れ

実装の流れは以下の通りです。
なお、今回の Proxy 認証方式は NTLM とします。

  1. HttpClient のインスタンスを生成
  2. Proxy 情報を設定
  3. Proxyの認証情報を設定(今回はNTLM認証)
  4. Method の生成(今回は GetMethod)
  5. Method の実行
  6. Response の読み込み
  7. Response の処理
  8. Connection リソースの開放

1.HttpClient のインスタンスを生成

HttpClientのインスタンスを以下のように生成します。

HttpClient client = new HttpClient();

2.Proxy 情報を設定

HttpClientのインスタンスからHostConfigurationのインスタンス を取得し、Proxy の ホスト 及び ポート番号を設定します。

client.getHostConfiguration().setProxy(proxyHost, proxyPort);

3.Proxyの認証情報を設定(今回はNTLM認証)

今回は NTLM認証 ですので、Credentials にはNTCredentialsを使用します。 NTCredentialsのコンストラクタで、ユーザ名、パスワード、ホスト、ドメインを指定します。

client.getState().setProxyCredentials(
    new AuthScope(proxyHost, proxyPort),
    new NTCredentials("userName", "password", "host", "domain")
);

4.Method の生成(今回は GetMethod)

今回は、GetMethodを使用して、 http://www.google.co.jp/ の内容を取得します。 GetMethodのコンストラクタで、URLを指定します。

GetMethod method = new GetMethod("http://www.google.co.jp/");

5.Method の実行

Methodを実行するには、HttpClientexecuteMethodを実行します。戻り値はHTTPステータスコードです。

int status = client.executeMethod(method);

6.Response の読み込み

Response の body を読む方法は 3つ用意されています。
method.getResponseBody()
body を byte 配列として返します。
method.getResponseBodyAsString()
body を 文字列として返します。文字列はデフォルトのエンコーディングが使用されます。
method.getResponseBodyAsStream()
body を Stream として返します。
今回はmethod.getResponseBody()を使用します。
byte[] responseBody = method.getResponseBody();

7.Response の処理

今回は、標準出力に取得した内容を出力します。

System.out.println(new String(responseBody));

8.Connection リソースの開放

Connection リソースは使用した後必ず開放しなければなりません。 finallyブロックでmethod.releaseConnection()メソッドを実行します。

method.releaseConnection();

ソースコード

・最終的なソースコードは以下のようになります。

TestProxy.java
import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
import org.apache.commons.httpclient.NTCredentials;
import org.apache.commons.httpclient.auth.AuthScope;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.params.HttpConnectionManagerParams;
import org.apache.commons.httpclient.HttpStatus;
import java.io.IOException;

class TestProxy {

    public static void main(String[] args) {

        String proxyHost = "192.168.0.210";  // Proxyのホスト
        int proxyPort = 8080;                // Proxyのポート番号

        // HttpClient の生成
        HttpClient client = new HttpClient();
        client.getHostConfiguration().setProxy(proxyHost, proxyPort);
        client.getState().setProxyCredentials(
            new AuthScope(proxyHost, proxyPort),
            new NTCredentials("userName", "password", "host", "domain")
        );

        // GetMethod の生成
        GetMethod method = new GetMethod("http://www.google.co.jp/");
        method.setDoAuthentication(true);

        try {

            // GetMethod の実行
            int status = client.executeMethod(method);
            if (status != HttpStatus.SC_OK) {
                throw new HttpException("Connection failed.");
            }

            // Response を取得して表示
            byte[] responseBody = method.getResponseBody();
            System.out.println(new String(responseBody));

        } catch (HttpException e) {
            System.err.println("Http error: " + e.getMessage());
            e.printStackTrace();
        } catch (IOException e) {
            System.err.println("I/O error: " + e.getMessage());
            e.printStackTrace();
        } finally {
            method.releaseConnection();
            method = null;
        }

    }

}