import java.io.IOException;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.net.SocketAddress;
import java.net.UnknownHostException;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import javax.net.SocketFactory;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;
import org.apache.commons.httpclient.ConnectTimeoutException;
import org.apache.commons.httpclient.params.HttpConnectionParams;
import org.apache.commons.httpclient.protocol.ProtocolSocketFactory;
public class MySSLProtocolSocketFactory implements ProtocolSocketFactory {
private SSLContext sslcontext = null;
private SSLContext createSSLContext() {
SSLContext sslcontext=null;
try {
sslcontext = SSLContext.getInstance("SSL");
//在HTTPS的证书未经权威机构认证的情况下,访问HTTPS站点;自己实现并覆盖JSSE缺省的证书信任管理器类
sslcontext.init(null, new TrustManager[]{new TrustAnyTrustManager()}, new java.security.SecureRandom());
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
}
return sslcontext;
}
private SSLContext getSSLContext() {
if (this.sslcontext == null) {
this.sslcontext = createSSLContext();
}
return this.sslcontext;
}
public Socket createSocket(Socket socket, String host, int port, boolean autoClose)
throws IOException, UnknownHostException {
return getSSLContext().getSocketFactory().createSocket(
socket,
host,
port,
autoClose
);
}
public Socket createSocket(String host, int port) throws IOException,
UnknownHostException {
return getSSLContext().getSocketFactory().createSocket(
host,
port
);
}
public Socket createSocket(String host, int port, InetAddress clientHost, int clientPort)
throws IOException, UnknownHostException {
return getSSLContext().getSocketFactory().createSocket(host, port, clientHost, clientPort);
}
public Socket createSocket(String host, int port, InetAddress localAddress,
int localPort, HttpConnectionParams params) throws IOException,
UnknownHostException, ConnectTimeoutException {
if (params == null) {
throw new IllegalArgumentException("Parameters may not be null");
}
int timeout = params.getConnectionTimeout();
SocketFactory socketfactory = getSSLContext().getSocketFactory();
if (timeout == 0) {
return socketfactory.createSocket(host, port, localAddress, localPort);
} else {
Socket socket = socketfactory.createSocket();
SocketAddress localaddr = new InetSocketAddress(localAddress, localPort);
SocketAddress remoteaddr = new InetSocketAddress(host, port);
socket.bind(localaddr);
socket.connect(remoteaddr, timeout);
return socket;
}
}
//自定义私有类
private static class TrustAnyTrustManager implements X509TrustManager {
//该方法检查客户端的证书,若不信任该证书则抛出异常。由于我们不需要对客户端进行认证,因此我们只需要执行默认的信任管理器的这个方法。
public void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException {
}
//该方法检查服务器的证书,若不信任该证书同样抛出异常。通过自己实现该方法,可以使之信任我们指定的任何证书。在实现该方法时,也可以简单的不做任何处理,即一个空的函数体,由于不会抛出异常,它就会信任任何证书。
public void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {
}
//返回受信任的X509证书数组。
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[]{};
}
}
}
/**
* 调用httpClient3.1 的方法
*
* @param data
* @param httpClient
* @return
*/
private static String httpRequest(String data, HttpClient httpClient) {
///////////////////优化配置参数
HttpConnectionManagerParams params =new HttpConnectionManagerParams();
//请求超时4秒钟 按照实际业务需求设置
params.setConnectionTimeout(4000);
//等待超市 按照实际业务需求设置
params.setSoTimeout(4000);
// 最大连接数
params.setMaxTotalConnections(500);
params.setDefaultMaxConnectionsPerHost(500);
params.setStaleCheckingEnabled(true);
HttpConnectionManager httpConnectionManager = new MultiThreadedHttpConnectionManager();
httpConnectionManager.setParams(params);
HttpClientParams httpClientParams = new HttpClientParams();
// 设置httpClient的连接超时,对连接管理器设置的连接超时是无用的
httpClientParams.setConnectionManagerTimeout(5000);
httpClient.setHttpConnectionManager(httpConnectionManager);
httpClient.setParams(httpClientParams);
///////////////////优化配置参数 end
Protocol myhttps = new Protocol("https", new MySSLProtocolSocketFactory(), port);
Protocol.registerProtocol("https", myhttps);
PostMethod postMethod = new PostMethod(httpsURL);
//设置请求报文的字符集
postMethod.addRequestHeader("Content-Type", "text/html;charset=GBK");
String respones = null;
postMethod.setRequestBody(data);
// 执行postMethod
try {
int statusCode = httpClient.executeMethod(postMethod);
// HttpClient对于要求接受后继服务的请求,象POST和PUT等不能自动处理转发
// 301或者302
if (statusCode == HttpStatus.SC_MOVED_PERMANENTLY || statusCode == HttpStatus.SC_MOVED_TEMPORARILY) {
// 从头中取出转向的地址
Header locationHeader = postMethod.getResponseHeader("location");
String location = null;
if (locationHeader != null) {
location = locationHeader.getValue();
loggerBoce.info("The page was redirected to:" + location);
} else {
loggerBoce.info("Location field value is null.");
}
}
respones = postMethod.getResponseBodyAsString();
} catch (HttpException e) {
loggerBoce.error(e.getMessage(), e);
} catch (IOException e) {
// 发生网络异常
loggerBoce.error(e.getMessage(), e);
} catch (Exception e) {
loggerBoce.error(e.getMessage(), e);
}finally{
//释放连接
if(null != postMethod){
postMethod.releaseConnection();
}
}
return respones;
}