參考:http://www.blogjava.net/alpha/archive/2007/01/22/95216.html
http://www.360doc.com/content/09/1201/18/203871_10149531.shtml
HttpClient是apache設計實現,用來簡化http客戶端與服務器端的網絡通信編程接口。目前,有commons-httpclient和httpclient倆個版本,前者最後版本是3.1,後者分爲HttpClient和HttpCore兩個部分,同時包含server和client端的API,版本號從4.0開始。我們儘量優先使用最新版本的httpclient。
commons-httpclient
1、GET/POST
a、get/post
private static final String host = "localhost";
private static final int port = 8080;
HttpClient client = new HttpClient();
client.getHostConfiguration.setHost(host,port,"http");
//get方式提交信息
GetMethod getMethod = new GetMethod("/index.jsp?key=520");
//獲取流
InputStream in = getMethod.getResponseBodyAsStream();
//post方式提交信息
PostMethod postMethod = new PostMethod("/index.jsp");
NameValuePair value1 = new NameValuePair("name","felix");
NameValuePair value2 = new NameValuePair("age",18);
postMethod.setRequestBody(new NameValuePair[][value1,value2]);
client.executeMethod(getMethod);
client.executeMethod(postMethod);
//記得釋放連接哦
getMethod.releaseConnection();
postMethod.releaseConnection();
b、head
HeadMethod head = new HeadMethod("http://www.csdn.net");
// 執行方法,並處理失敗的請求.
...
// 取回應答包的頭字段信息.
Header[] headers = head.getResponseHeaders();
// 只取回最後修改日期字段的信息.
String lastModified = head.getResponseHeader("last-modified").getValue();
c、post (使用HttpPost)
DefaultHttpClient httpclient = new DefaultHttpClient();
HttpPost postMethod = new HttpPost("http://reg.csdn.net"); //注意用post
//參數
List<NameValuePair> list = new ArrayList<NameValuePair>();
list.add(new BasicNameValuePair("username", "felix"));
list.add(new BasicNameValuePair("password", "****"));
list.add(new BasicNameValuePair("age", "22"));
list.add(new BasicNameValuePair("address", "beijing"));
list.add(new BasicNameValuePair("sex", "male"));
postMethod.setEntity(new UrlEncodedFormEntity(list, HTTP.UTF_8));
HttpResponse response = httpclient.execute(postMethod);
2、重定向
狀態碼 HttpServletResponse常量 詳細
301 SC_MOVED_PERMANENTLY 頁面已經永久移動到另外一個新地址
302 SC_MOVED_TEMPORARILY 頁面暫時移動到另外一個新地址
303 SC_SEE_OTHER 客戶端請求的地址必須通過另外的URL來訪問
307 SC_TEMPORARY_REDIRECT 同SC_MOVED_TEMPORARILY
client.executeMethod(postMethod);
postMethod.releaseConnection():
int status=postMethod.getStatusCode();
//是否重定向
if((statuscode == HttpStatus.SC_MOVED_TEMPORARILY) ||
(statuscode == HttpStatus.SC_MOVED_PERMANENTLY) ||
(statuscode == HttpStatus.SC_SEE_OTHER) ||
(statuscode == HttpStatus.SC_TEMPORARY_REDIRECT)){
//新地址
Header header = postMethod.getResponseHeader("location");
String uri = header.getValue()==null?header.getValue():"";
}
3、超時和重試(retry)
a、設置超時
client.setConnectionTimeout(SysGlobals.TIMEOUT);
或者
client.setTimeOut(SysGlobals.TIMEOUT);
這兩個方法已經@Deprecated
b、設置get/post請求超時
getMethod.getParams().setParameter(HttpParams.SO_TIMEOUT,10000);
postMethod.getParams().setParameter(HttpParams.SO_TIMEOUT,10000);
c、設置http連接超時5s
client.getHttpConnectionManager().getParams().setConnectionTimeout(5000);
d、設置retry
DefaultMethodRetryHandler retry = new DefaultMethodRetryHandler();
retry.setRequestSentRetryEnabled(true);
retry.setRetryCount(4);
method.setMethodRetryHandler(retry);
client.executeMethod(method);
4、提交xml格式參數
import java.io.File;
import java.io.FileInputStream;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.methods.EntityEnclosingMethod;
import org.apache.commons.httpclient.methods.PostMethod;
/**
*用來演示提交XML格式數據的例子
*/
public class PostXMLClient {
public static void main(String[] args) throws Exception {
File input = new File("/home/lrq1988/test.xml");
PostMethod post = new PostMethod(“http://localhost:8080/httpclient/xml.jsp”);
// 設置請求的內容直接從文件中讀取
post.setRequestBody( new FileInputStream(input));
if (input.length() < Integer.MAX_VALUE)
post.setRequestContentLength(input.length());
else
post.setRequestContentLength(EntityEnclosingMethod.CONTENT_LENGTH_CHUNKED);
// 指定請求內容的類型
post.setRequestHeader( "Content-type" , "text/xml; charset=GBK" );
HttpClient httpclient = new HttpClient();
int result = httpclient.executeMethod(post);
System.out.println( "Response status code: " + result);
System.out.println( "Response body: " );
System.out.println(post.getResponseBodyAsString());
post.releaseConnection();
}
}
5、文件上傳
MultipartPostMethod filePost = new MultipartPostMethod(targetURL);
filePost.addParameter( "fileName" , targetFilePath);
HttpClient client = new HttpClient();
// 由於要上傳的文件可能比較大 , 因此在此設置最大的連接超時時間
client.getHttpConnectionManager(). getParams().setConnectionTimeout(5000);
int status = client.executeMethod(filePost);
6、多線程模式
多線程同時訪問httpclient,例如同時從一個站點上下載多個文件。對於同一個HttpConnection同一個時間只能有一個線程訪問,爲了保證多線程工作環境下不產生衝突,httpclient使用了一個多線程連接管理器的類:MultiThreadedHttpConnectionManager,要使用這個類很簡單,只需要在構造HttpClient實例的時候傳入即可,代碼如下:
MultiThreadedHttpConnectionManager connectionManager =
new MultiThreadedHttpConnectionManager();
HttpClient client = new HttpClient(connectionManager);
以後儘管訪問client實例即可。
7、Cookie
HttpClient client = new HttpClient();
client.getParams().setCookiePolicy(CookiePolicy.RFC_2109);//RFC_2109之外,還有其他cookie協議
HttpState state = new HttpState();
Cookie cookie = new Cookie();
cookie.setDomain("www.csdn.net");
cookie.setPath("/");
cookie.setName("name");
cookie.setValue("value");
state.addCookie(cookie);
client.setState(state);
Cookie[] cookies = client.getState().getCookies();
for(){}
8、代理
client.getHostConfiguration().setProxy("192.168.0.1",9527);
client.getParams.setAuthenticationPreemptive(true);//使用搶先認證,否則沒有資格
/*
MyProxyCredentialsProvider實現了CredentialsProvider接口,返回代理的credential(username/password)
*/
client.setParams.setParameter(CredentialsProvider.PROVIDER,
new MyProxyCredentialsProvider());
client.getState().setProxyCredentials(new AuthScop("192.168.0.1",
AuthScope.ANY_PORT,//任意端口
AuthScope.ANY_REALM,//任意域
new UsernamePasswordCredentials("username","password")));//代理的用戶名、密碼
9、https
Class EasySSLProtocolSocketFactory : http://juliusdavies.ca/commons-ssl/javadocs/org/apache/commons/httpclient/contrib/ssl/EasySSLProtocolSocketFactory.html
針對特定主機使用自定義協議套接字工廠
Protocol easyhttps =
new Protocol("https", new EasySSLProtocolSocketFactory(), 443);
HttpClient client = new HttpClient();
client.getHostConfiguration().setHost("localhost", 443, easyhttps);
// use relative url only
GetMethod httpget = new GetMethod("/");
client.executeMethod(httpget);
使用http method之前,先註冊https,下面的請求都將默認使用這個
Protocol easyhttps =
new Protocol("https", new EasySSLProtocolSocketFactory(), 443);
Protocol.registerProtocol("https", easyhttps);
HttpClient client = new HttpClient();
GetMethod httpget = new GetMethod("https://localhost/");
client.executeMethod(httpget);