Package net.matuschek.http.connection

Source Code of net.matuschek.http.connection.HttpsHelper

package net.matuschek.http.connection;

/*********************************************
    Copyright (c) 2002 by Daniel Matuschek
*********************************************/

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.net.InetAddress;
import java.net.Socket;

import javax.net.ssl.SSLSocket;
import javax.net.ssl.SSLSocketFactory;

/*
* How to use SSL with a proxy:
* - http://java.sun.com/j2se/1.4/docs/guide/security/jsse/
*    samples/sockets/client/SSLSocketClientWithTunneling.java
*/


/**
* An helper class to provide SSL connections with and without proxy
*
* @author Daniel Matuschek <daniel@matuschek.net>
* @version $Id: HttpsHelper.java,v 1.5 2002/09/06 13:03:52 matuschd Exp $
*/
public class HttpsHelper {

  /** should it use a proxy server ? */
  boolean useProxy = false;

  /** Proxy host */
  InetAddress proxyHost = null;

  /** Proxy port */
  int proxyPort = 0;

 

  /**
   * Simple costructor that initialized an HttpsHelper
   */
  public HttpsHelper() {
  }


  /**
   * Constructor that initializes the HttpsHelper an
   * also sets the proxy settings.
   */
  public HttpsHelper(InetAddress proxyHost, int proxyPort, boolean useProxy) {
    this.proxyHost = proxyHost;
    this.proxyPort = proxyPort;
    this.useProxy = useProxy;
  }



  /**
   * Creates a new HTTPS connection to the defined host/port
   *
   * @param host full qualified hostname or ip address of the host
   * to contact
   * @param port destination prot on the server to connect
   *
   * @exception IOException, if the connection cannot be established
   *
   * @return an HttpConnection object with the established conection
   */
  public HttpConnection createHttpsConnection(String host, int port)
    throws IOException
  {
    HttpConnection connection = null;
    SSLSocketFactory factory = (SSLSocketFactory)SSLSocketFactory.getDefault();
    SSLSocket socket = null;

    if (! useProxy) {
     
      socket = (SSLSocket)factory.createSocket(host,port);

    } else {
     
      Socket tunnel = new Socket(proxyHost, proxyPort);
      doTunnelHandshake(tunnel, host, port);
     
      /*
       * Ok, let's overlay the tunnel socket with SSL.
       */
      socket = (SSLSocket)factory.createSocket(tunnel, host, port, true);
     
      /*
       * send http request
       *
       * See SSLSocketClient.java for more information about why
       * there is a forced handshake here when using PrintWriters.
       */
      socket.startHandshake();
    }

    connection = new HttpConnection(socket);

    return connection;

  }


  /**
   * Tell our tunnel where we want to CONNECT, and look for the
   * right reply.  Throw IOException if anything goes wrong.
   */
  private void doTunnelHandshake(Socket tunnel, String host, int port)
    throws IOException
  {
    OutputStream out = tunnel.getOutputStream();
    String msg = "CONNECT " + host + ":" + port + " HTTP/1.0\n"
      + "User-Agent: JoBo/1.4beta"
      + "\r\n\r\n";
    byte[] b;
    try {
      /*
       * We really do want ASCII7 -- the http protocol doesn't change
       * with locale.
       */
      b = msg.getBytes("ASCII7");
    } catch (UnsupportedEncodingException ignored) {
      /*
       * If ASCII7 isn't there, something serious is wrong, but
       * Paranoia Is Good (tm)
       */
      b = msg.getBytes();
    }
    out.write(b);
    out.flush();
   
    /*
     * We need to store the reply so we can create a detailed
     * error message to the user.
     */
    byte[] reply = new byte[200];
    int  replyLen = 0;
    int newlinesSeen = 0;
    boolean headerDone = false/* Done on first newline */
   
    InputStream  in = tunnel.getInputStream();
    while (newlinesSeen < 2) {
      int i = in.read();
      if (i < 0) {
  throw new IOException("Unexpected EOF from proxy");
      }
      if (i == '\n') {
  headerDone = true;
  ++newlinesSeen;
      } else if (i != '\r') {
  newlinesSeen = 0;
  if (!headerDone && replyLen < reply.length) {
    reply[replyLen++] = (byte) i;
  }
      }
    }
   
    /*
     * Converting the byte array to a string is slightly wasteful
     * in the case where the connection was successful, but it's
     * insignificant compared to the network overhead.
     */
    String replyStr;
    try {
      replyStr = new String(reply, 0, replyLen, "ASCII7");
    } catch (UnsupportedEncodingException ignored) {
      replyStr = new String(reply, 0, replyLen);
    }
   
    /* We asked for HTTP/1.0, so we should get that back */
    if (!replyStr.startsWith("HTTP/1.0 200")) {
      throw new IOException("Unable to tunnel through proxy"
          + ".  Proxy returns \"" + replyStr + "\"");
    }
   
    /* tunneling Handshake was successful! */
  }
 


}
TOP

Related Classes of net.matuschek.http.connection.HttpsHelper

TOP
Copyright © 2015 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.