前言
超文本传输协议(HTTP)也许是当今互联网上使用的最重要的协议了。Web服务,有网络功能的设备和网络计算的发展,都持续扩展了HTTP协议的角色,超越了用户使用的Web浏览器范畴,同时,也增加了需要HTTP协议支持的应用程序的数量。
尽管java.net包提供了基本通过HTTP访问资源的功能,但它没有提供全面的灵活性和其它很多应用程序需要的功能。HttpClient就是寻求弥补这项空白的组件,通过提供一个有效的,保持更新的,功能丰富的软件包来实现客户端最新的HTTP标准和建议。
为扩展而设计,同时为基本的HTTP协议提供强大的支持,HttpClient组件也许就是构建HTTP客户端应用程序,比如web浏览器,web服务端,利用或扩展HTTP协议进行分布式通信的系统的开发人员的关注点。
1. HttpClient的范围
基于HttpCore[http://hc.apache.org/httpcomponents-core/index.html]的客户端HTTP运输实现库
基于经典(阻塞)I/O
内容无关
2. 什么是HttpClient不能做的
HttpClient不是一个浏览器。它是一个客户端的HTTP通信实现库。HttpClient的目标是发送和接收HTTP报文。HttpClient不会去缓存内容,执行嵌入在HTML页面中的java script代码,猜测内容类型,重新格式化请求/重定向URI,或者其它和HTTP运输无关的功能。
第一章 基础
1.1 执行请求
HttpClient最重要的功能是执行HTTP方法。一个HTTP方法的执行包含一个或多个HTTP请求/HTTP响应交换,通常由HttpClient的内部来处理。而期望用户提供一个要执行的请求对象,而HttpClient期望传输请求到目标服务器并返回对应的响应对象,或者当执行不成功时抛出异常。
很自然地,HttpClient API的主要切入点就是定义描述上述规约的HttpClient接口。
这里有一个很简单的请求执行过程的示例:
HttpClient httpclient = new DefaultHttpClient();
HttpGet httpget = new HttpGet(“http://localhost/”);
HttpResponse response = httpclient.execute(httpget);
HttpEntity entity = response.getEntity();
if (entity != null) {
InputStream instream = entity.getContent();
int l;
byte[] tmp = new byte[2048];
while ((l = instream.read(tmp)) != -1) {
}
}
1.1.1 HTTP请求
所有HTTP请求有一个组合了方法名,请求URI和HTTP协议版本的请求行。
HttpClient支持所有定义在HTTP/1.1版本中的HTTP方法:GET,HEAD,POST,PUT,DELETE,TRACE和OPTIONS。对于每个方法类型都有一个特殊的类:HttpGet,HttpHead,HttpPost,HttpPut,HttpDelete,HttpTrace和HttpOptions。
请求的URI是统一资源定位符,它标识了应用于哪个请求之上的资源。HTTP请求URI包含一个协议模式,主机名称,可选的端口,资源路径,可选的查询和可选的片段。
HttpGet httpget = new HttpGet(
“http://www.google.com/search?hl=en&q=httpclient&btnG=Google+Search&aq=f&oq=”);
HttpClient提供很多工具方法来简化创建和修改执行URI。
URI也可以编程来拼装:
URI uri = URIUtils.createURI(“http”, “www.google.com”, -1, “/search”,
“q=httpclient&btnG=Google+Search&aq=f&oq=”, null);
HttpGet httpget = new HttpGet(uri);
System.out.println(httpget.getURI());
输出内容为:
http://www.google.com/search?q=httpclient&btnG=Google+Search&aq=f&oq=
查询字符串也可以从独立的参数中来生成:
List qparams = new ArrayList();
qparams.add(new BasicNameva luePair(“q”, “httpclient”));
qparams.add(new BasicNameva luePair(“btnG”, “Google Search”));
qparams.add(new BasicNameva luePair(“aq”, “f”));
qparams.add(new BasicNameva luePair(“oq”, null));
URI uri = URIUtils.createURI(“http”, “www.google.com”, -1, “/search”,
URLEncodedUtils.format(qparams, “UTF-8″), null);
HttpGet httpget = new HttpGet(uri);
System.out.println(httpget.getURI());
输出内容为:
http://www.google.com/search?q=httpclient&btnG=Google+Search&aq=f&oq=
1.1.2 HTTP响应
HTTP响应是由服务器在接收和解释请求报文之后返回发送给客户端的报文。响应报文的第一行包含了协议版本,之后是数字状态码和相关联的文本段。
HttpResponse response = new BasicHttpResponse(HttpVersion.HTTP_1_1,
HttpStatus.SC_OK, “OK”);
System.out.println(response.getProtocolVersion());
System.out.println(response.getStatusLine().getStatusCode());
System.out.println(response.getStatusLine().getReasonPhrase());
System.out.println(response.getStatusLine().toString());
输出内容为:
HTTP/1.1
200
OK
HTTP/1.1 200 OK
1.1.3 处理报文头部
一个HTTP报文可以包含很多描述如内容长度,内容类型等信息属性的头部信息。
HttpClient提供获取,添加,移除和枚举头部信息的方法。
HttpResponse response = new BasicHttpResponse(HttpVersion.HTTP_1_1,
HttpStatus.SC_OK, “OK”);
response.addHeader(“Set-Cookie”,
“c1=a; path=/; domain=localhost”);
response.addHea