通常使用一些 http 的客户端工具包,如 apache 等,无法访问 https 的链接(使用 HTTPS 专用的Client ),主要是因为底层实现本身就是两套通信。
而且 https 一般需要有证书信任才行,实际上这个是客户端的限制,由于项目中需要同时调用 http 和 https(连证书都没有的,没办法),所以只有自己写一个了。
记录一下,同时支持HTTP和HTTPS访问。
基本上访问一个HTTP的代码如下,兼容了HTTPS访问(没有证书认证的,如果想访问支付宝等,需要配置一个访问的公钥)
public class HttpClient {
private String charset = "UTF-8";
private boolean safe = false;
private String url;
Map<String, String> headers = null;
public HttpClient(String url) {
this.url = url;
this.safe = url.startsWith("https");
}
public HttpClient(String url, String charset) {
this.url = url;
this.charset = charset;
this.safe = url.startsWith("https");
}
public void setHeader(Map<String, String> headers) {
this.headers = headers;
}
public String get() throws IOException {
if (this.safe) {
return this.sendhttpsReq("GET", "", headers);
} else {
return this.sendhttpReq("GET", "", headers);
}
}
public String post(String httpStr) throws IOException {
if (this.safe) {
return this.sendhttpsReq("POST", "", headers);
} else {
return this.sendhttpReq("POST", "", headers);
}
}
/**
* 发送http请求.
* @param url
* :请求url
* @param httpStr
* :请求消息体
* @param headers
* :请求消息头
* @return http返回消息体,null表示失败
* @throws IOException
*/
private final String sendhttpReq(String method, String httpStr,
Map<String, String> headers) throws IOException {
HttpURLConnection conn = (HttpURLConnection) new URL(url)
.openConnection();
conn.setRequestMethod(method);
conn.setDoOutput(true);
conn.setDoInput(true);
conn.setRequestProperty("Content-Type", "text/heml");
if (headers != null) {
for (Map.Entry<String, String> entry : headers.entrySet()) {
conn.setRequestProperty(entry.getKey(), entry.getValue());
}
}
OutputStream out = conn.getOutputStream();
out.write(httpStr.getBytes(charset));
out.flush();
BufferedReader in = new BufferedReader(new InputStreamReader(
conn.getInputStream()));
if (200 != conn.getResponseCode()) {
return null;
}
StringBuilder result = new StringBuilder(100);
char[] buf = new char[512];
int byteread = 0;
while ((byteread = in.read(buf)) != -1) {
result.append(buf, 0, byteread);
}
return result.toString();
}
/**
* 发送https请求.
* @param url
* :请求url
* @param httpStr
* :请求消息体
* @param headers
* :请求消息头
* @return http返回消息体,null表示失败
* @throws IOException
*/
private final String sendhttpsReq(String method, String httpStr,
Map<String, String> headers) {
HttpsURLConnection conn = null;
OutputStream out = null;
try {
SSLContext ctx = SSLContext.getInstance("TLS");
ctx.init(new KeyManager[0], new TrustManager[] {new DefaultTrustManager()}, new SecureRandom());
SSLContext.setDefault(ctx);
conn = (HttpsURLConnection) new URL(url).openConnection();
conn.setRequestMethod(method);
conn.setDoOutput(true);
conn.setDoInput(true);
conn.setHostnameVerifier(new HostnameVerifier(){
@Override
public boolean verify(String hostname, SSLSession session) {
return true;
}
});
conn.setRequestProperty("Content-Type", "text/html");
if (headers != null) {
for (Map.Entry<String, String> entry : headers.entrySet()) {
conn.setRequestProperty(entry.getKey(), entry.getValue());
}
}
out = conn.getOutputStream();
out.write(httpStr.getBytes(charset));
out.flush();
BufferedReader in = new BufferedReader(new InputStreamReader(
conn.getInputStream()));
if (200 != conn.getResponseCode()) {
return null;
}
StringBuilder result = new StringBuilder(100);
char[] buf = new char[512];
int byteread = 0;
while ((byteread = in.read(buf)) != -1) {
result.append(buf, 0, byteread);
}
return result.toString();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (KeyManagementException e) {
e.printStackTrace();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return "";
}
private static class DefaultTrustManager implements X509TrustManager {
@Override
public void checkClientTrusted(X509Certificate[] arg0, String arg1)
throws CertificateException {
}
@Override
public void checkServerTrusted(X509Certificate[] arg0, String arg1)
throws CertificateException {
}
@Override
public X509Certificate[] getAcceptedIssuers() {
return null;
}
}
public static void main(String[] args){
HttpClient client = new HttpClient("http://www.qq.com/");
try {
System.out.println(client.get());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
};
HttpClient client2 = new HttpClient("https://localhost:8443/login");
try {
System.out.println(client2.post("username=d&password=ddd"));
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
};
}
}