Rover12421's Blog

The End.

HttpClient 使用socks代理

      HttpClient使用HTTP代理很简单,但是用socks代理就稍微复杂点。下面是参考HttpClient官方的例子,在其基础上增加了代理验证。

import java.io.IOException;
import java.net.Authenticator;
import java.net.InetSocketAddress;
import java.net.PasswordAuthentication;
import java.net.Proxy;
import java.net.Socket;
import java.net.SocketTimeoutException;
import java.net.UnknownHostException;

import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.conn.ConnectTimeoutException;
import org.apache.http.conn.scheme.Scheme;
import org.apache.http.conn.scheme.SchemeSocketFactory;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.params.HttpConnectionParams;
import org.apache.http.params.HttpParams;
import org.apache.http.util.EntityUtils;

public class SocksProxy {
   
    public static void main(String[] args) throws Exception {       
        DefaultHttpClient httpclient = new DefaultHttpClient();
       
        try {
            Authenticator.setDefault(new SocksAuthenticator(“user”, “pwd”));
       
            httpclient.getParams().setParameter(“socks.host”, “socksHost”);
            httpclient.getParams().setParameter(“socks.port”, sockPort);
       
            httpclient.getConnectionManager().getSchemeRegistry().register(
                    new Scheme(“http”, 80, new SocksSchemeSocketFactory()));
           
            HttpGet get = new HttpGet(http://city.ip138.com/city.asp);
            HttpResponse rsp = httpclient.execute(get);
            HttpEntity entity = rsp.getEntity();
            System.out.println(rsp.getStatusLine());
            Header[] headers = rsp.getAllHeaders();
            for (int i = ; i < headers.length; i++) {
                System.out.println(headers[i]);
            }
            System.out.println(“——————————”);
           
            if (entity != null) {
                System.out.println(EntityUtils.toString(entity, “gb2312”));
            }
        } finally {
            httpclient.getConnectionManager().shutdown();
        }
       
    }
   
    static class SocksSchemeSocketFactory implements SchemeSocketFactory {

        @Override
        public Socket connectSocket(final Socket socket, final InetSocketAddress remoteAddress,
                final InetSocketAddress localAddress, final HttpParams params) throws IOException,
                UnknownHostException, ConnectTimeoutException {
            // TODO Auto-generated method stub
            if (remoteAddress == null) {
                throw new IllegalArgumentException(“Remote address may not be null”);
            }
            if (params == null) {
                throw new IllegalArgumentException(“HTTP parameters may not be null”);
            }
            Socket sock;
            if (socket != null) {
                sock = socket;
            } else {
                sock = createSocket(params);
            }
            if (localAddress != null) {
                sock.setReuseAddress(HttpConnectionParams.getSoReuseaddr(params));
                sock.bind(localAddress);
            }
            int timeout = HttpConnectionParams.getConnectionTimeout(params);
            try {
                sock.connect(remoteAddress, timeout);
            } catch (SocketTimeoutException ex) {
                throw new ConnectTimeoutException(“Connect to ” + remoteAddress.getHostName() + “/” + remoteAddress.getAddress() + “ time out”);
            }
            return sock;
        }

        @Override
        public Socket createSocket(final HttpParams params) throws IOException {
            // TODO Auto-generated method stub
            if (params == null) {
                throw new IllegalArgumentException(“Http parameters may not be null”);
            }
            String proxyHost = (String) params.getParameter(“socks.host”);
            Integer proxyPort = (Integer) params.getParameter(“socks.port”);
           
            InetSocketAddress socksAddr = new InetSocketAddress(proxyHost, proxyPort);
            Proxy proxy = new Proxy(Proxy.Type.SOCKS, socksAddr);
            return new Socket(proxy);
        }

        @Override
        public boolean isSecure(final Socket sock) throws IllegalArgumentException {
            // TODO Auto-generated method stub
            return false;
        }   
       
    }
   
    static class SocksAuthenticator extends Authenticator {
        private String username;
        private String    password;

        public SocksAuthenticator(final String user, final String pass) {
            username = user;
            password = pass;
        }

        protected PasswordAuthentication getPasswordAuthentication() {
            if (username != null && password != null) {
                return new PasswordAuthentication(username, password.toCharArray());
            }
            else {
                return null;
            }
        }
    }
}

Socks验证使用的方式和使用Java全局的Socks代理验证方式是一样的。

Comments