panda.net.http.HttpClient Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of panda-core Show documentation
Show all versions of panda-core Show documentation
Panda Core is the core module of Panda Framework, it contains commonly used utility classes similar to apache-commons.
package panda.net.http;
import java.io.IOException;
import java.io.OutputStream;
import java.net.CookieHandler;
import java.net.CookieManager;
import java.net.CookiePolicy;
import java.net.HttpURLConnection;
import java.net.Proxy;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import panda.io.MimeTypes;
import panda.io.Streams;
import panda.lang.Arrays;
import panda.lang.Asserts;
import panda.lang.Numbers;
import panda.lang.Strings;
import panda.lang.Systems;
import panda.lang.time.StopWatch;
import panda.log.Log;
import panda.log.Logs;
import panda.net.URLHelper;
/**
*/
public class HttpClient {
protected static Log log = Logs.getLog(HttpClient.class);
public static HttpResponse get(String url) throws IOException {
return send(url, HttpMethod.GET, null);
}
public static HttpResponse get(String url, int timeout) throws IOException {
return send(url, HttpMethod.GET, null, null, timeout);
}
public static HttpResponse get(String url, Map params) throws IOException {
return send(url, HttpMethod.GET, params);
}
public static HttpResponse post(String url) throws IOException {
return send(url, HttpMethod.POST, null);
}
public static HttpResponse post(String url, Map params) throws IOException {
return send(url, HttpMethod.POST, params);
}
public static HttpResponse post(String url, byte[] body) throws IOException {
return send(url, HttpMethod.POST, null, body, 0);
}
public static HttpResponse send(String url, String method, Map params) throws IOException {
return send(url, method, params, null, 0);
}
public static HttpResponse send(String url, String method, Map params, byte[] body, int timeout) throws IOException {
HttpRequest hr = HttpRequest.create(url, method, params);
hr.setDefault();
hr.setBody(body);
HttpClient hc = new HttpClient(hr);
hc.setReadTimeout(timeout);
return hc.send();
}
//---------------------------------------------------------------------
protected HttpURLConnection httpconn;
protected HttpRequest request;
protected HttpResponse response;
protected Proxy proxy;
/**
* connection timeout (default: 30s)
*/
protected int connTimeout = 30000;
/**
* read timeout (default: 300s)
*/
protected int readTimeout = 300000;
protected boolean autoRedirect = false;
protected boolean sslHostnameCheck = true;
protected boolean sslSniExtension = true;
protected String[] sslProtocols;
static {
if (Systems.JAVA_MAJOR_VERSION < 7) {
// fix error: java.net.ProtocolException: Server redirected too many times (JDK1.6)
// see http://stackoverflow.com/questions/11022934/getting-java-net-protocolexception-server-redirected-too-many-times-error
CookieHandler.setDefault(new CookieManager(null, CookiePolicy.ACCEPT_ALL));
}
}
public HttpClient() {
this(new HttpRequest());
}
public HttpClient(boolean autoRedirect) {
this(new HttpRequest(), autoRedirect);
}
public HttpClient(HttpRequest request) {
this(request, true);
}
public HttpClient(HttpRequest request, boolean autoRedirect) {
this.autoRedirect = autoRedirect;
setRequest(request);
}
/**
* @return the request
*/
public HttpRequest getRequest() {
return request;
}
/**
* @param request the request to set
*/
public void setRequest(HttpRequest request) {
Asserts.notNull(request, "the request object is null");
this.request = request;
}
/**
* @return the response
*/
public HttpResponse getResponse() {
return response;
}
/**
* @return the autoRedirect
*/
public boolean isAutoRedirect() {
return autoRedirect;
}
/**
* @param autoRedirect the autoRedirect to set
*/
public void setAutoRedirect(boolean autoRedirect) {
this.autoRedirect = autoRedirect;
}
/**
* @return the sslHostnameCheck
*/
public boolean isSslHostnameCheck() {
return sslHostnameCheck;
}
/**
* @param sslHostnameCheck the sslHostnameCheck to set
*/
public void setSslHostnameCheck(boolean sslHostnameCheck) {
this.sslHostnameCheck = sslHostnameCheck;
}
/**
* @return the sslSniExtension
*/
public boolean isSslSniExtension() {
return sslSniExtension;
}
/**
* @param sslSniExtension the sslSniExtension to set
*/
public void setSslSniExtension(boolean sslSniExtension) {
this.sslSniExtension = sslSniExtension;
}
/**
* @return the sslProtocols
*/
public String[] getSslProtocols() {
return sslProtocols;
}
/**
* @param sslProtocols the sslProtocols to set
*/
public void setSslProtocols(String ... sslProtocols) {
this.sslProtocols = sslProtocols;
}
/**
* @return the connTimeout
*/
public int getConnTimeout() {
return connTimeout;
}
/**
* @param connTimeout the connTimeout to set
*/
public void setConnTimeout(int connTimeout) {
if (connTimeout > 0) {
this.connTimeout = connTimeout;
}
}
/**
* @return the readTimeout
*/
public int getReadTimeout() {
return readTimeout;
}
/**
* @param readTimeout the readTimeout to set
*/
public void setReadTimeout(int readTimeout) {
if (readTimeout > 0) {
this.readTimeout = readTimeout;
}
}
/**
* @return the proxy
*/
public Proxy getProxy() {
return proxy;
}
/**
* @param proxy the proxy to set
*/
public void setProxy(Proxy proxy) {
this.proxy = proxy;
}
public HttpResponse doGet() throws IOException {
request.setMethod(HttpMethod.GET);
return send();
}
public HttpResponse doPost() throws IOException {
request.setMethod(HttpMethod.POST);
return send();
}
public HttpResponse send() throws IOException {
if (!autoRedirect) {
return doSend();
}
doSend();
if (!response.isMoved()) {
return response;
}
String url = request.getURL().toString();
Set urls = new HashSet();
urls.add(url);
request.setMethod(HttpMethod.GET);
request.setParams(null);
while (true) {
String location = response.getHeader().getString(HttpHeader.LOCATION);
url = URLHelper.resolveURL(url, location);
if (Strings.isEmpty(url)) {
return response;
}
if (urls.contains(url)) {
log.info("infinite redirect loop detected: " + url);
return response;
}
urls.add(url);
request.setUrl(url);
doSend();
if (!response.isMoved()) {
return response;
}
}
}
protected HttpResponse doSend() throws IOException {
if (log.isTraceEnabled()) {
log.trace(request.toString(102400));
}
else if (log.isDebugEnabled()) {
log.debug(request.toString(1024));
}
else if (log.isInfoEnabled()) {
log.info(request.getMethod() + ": " + request.getURL());
}
StopWatch sw = new StopWatch();
if (request.isPost()) {
openConnection();
setupRequestHeader();
setupDoInputOutputFlag();
OutputStream os = httpconn.getOutputStream();
request.writeBody(os);
}
else {
openConnection();
setupRequestHeader();
}
createResponse();
if (log.isDebugEnabled()) {
StringBuilder msg = new StringBuilder();
msg.append(request.getMethod()).append(' ').append(request.getURL())
.append(" - ").append(response.getStatusLine());
msg.append(" (");
if (response.getContentLength() != null) {
msg.append(Numbers.formatSize(response.getContentLength())).append(" / ");
}
msg.append(sw).append(')');
if (response.getHeader() != null) {
msg.append(Streams.EOL);
response.getHeader().write(msg);
}
String text = response.getContentText(log.isTraceEnabled() ? 10240 : 1024);
if (Strings.isNotEmpty(text)) {
msg.append(Streams.EOL).append(text);
}
if (log.isTraceEnabled()) {
log.trace(msg.toString());
}
else {
log.debug(msg.toString());
}
}
else if (log.isInfoEnabled()) {
log.info(response.getStatusLine() + " : " + request.getURL());
}
return response;
}
protected void createResponse() throws IOException {
response = new HttpResponse(request.getURL(), httpconn);
}
protected void setupDoInputOutputFlag() {
httpconn.setDoInput(true);
httpconn.setDoOutput(true);
}
protected void openConnection() throws IOException {
if (proxy != null) {
httpconn = (HttpURLConnection)request.getURL().openConnection(proxy);
}
else {
httpconn = (HttpURLConnection)request.getURL().openConnection();
}
if (!sslHostnameCheck) {
Https.disableHostnameCheck(httpconn);
}
if (!sslSniExtension) {
Https.disableSniExtension(httpconn);
}
if (Arrays.isNotEmpty(sslProtocols)) {
Https.setProtocols(httpconn, sslProtocols);
}
httpconn.setConnectTimeout(connTimeout);
httpconn.setReadTimeout(readTimeout);
httpconn.setInstanceFollowRedirects(false);
}
protected void setupRequestHeader() {
Https.setupRequestHeader(httpconn, request.getURL(), request.getHeader());
if (request.isPostFile()) {
httpconn.setRequestProperty(HttpHeader.CONTENT_TYPE, MimeTypes.MULTIPART_FORM_DATA + "; boundary=" + request.getMultipartBoundary());
}
else if (request.isPostForm()) {
httpconn.setRequestProperty(HttpHeader.CONTENT_TYPE, MimeTypes.X_WWW_FORM_URLECODED + "; charset=" + request.getEncoding());
}
}
}