一、httpClient简介
使用场景:
爬虫
多系统之间接口交互
二、使用HttpClient获取网页内容
-导入依赖
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>4.5.13</version>
</dependency>
public class HttpURLConnTest { /** * 使用jdk原生的api来请求网页 */ @Test public void test() throws Exception { // 打开浏览器 CloseableHttpClient httpClient = HttpClientBuilder.create().build(); // 输入url地址 HttpGet httpGet = new HttpGet("https://www.baidu.com/"); CloseableHttpResponse response = null; try { // 敲回车,发送请求,获取响应 response = httpClient.execute(httpGet); // 获取内容 String result = EntityUtils.toString(response.getEntity(), "utf-8"); System.out.println(result); } catch (IOException e) { e.printStackTrace(); }finally { try { if (response != null) { response.close(); } if (httpGet != null) { httpGet.releaseConnection(); } if (httpClient != null) { httpClient.close(); } } catch (IOException e) { e.printStackTrace(); } } } }
-可以看到运行的结果是百度的源代码
<!DOCTYPE html> <!--STATUS OK--><html> <head><meta http-equiv=content-type content=text/html;charset=utf-8><meta http-equiv=X-UA-Compatible content=IE=Edge><meta content=always name=referrer><link rel=stylesheet type=text/css href=https://ss1.bdstatic.com/5eN1bjq8AAUYm2zgoY3K/r/www/cache/bdorz/baidu.min.css><title>百度一下,你就知道</title></head> <body link=#0000cc> <div id=wrapper> <div id=head> <div class=head_wrapper> <div class=s_form> <div class=s_form_wrapper> <div id=lg> <img hidefocus=true src=//www.baidu.com/img/bd_logo1.png width=270 height=129> </div> <form id=form name=f action=//www.baidu.com/s class=fm> <input type=hidden name=bdorz_come value=1> <input type=hidden name=ie value=utf-8> <input type=hidden name=f value=8> <input type=hidden name=rsv_bp value=1> <input type=hidden name=rsv_idx value=1> <input type=hidden name=tn value=baidu><span class="bg s_ipt_wr"><input id=kw name=wd class=s_ipt value maxlength=255 autocomplete=off autofocus=autofocus></span><span class="bg s_btn_wr"><input type=submit id=su value=百度一下 class="bg s_btn" autofocus></span> </form> </div> </div> <div id=u1> <a href=http://news.baidu.com name=tj_trnews class=mnav>新闻</a> <a href=https://www.hao123.com name=tj_trhao123 class=mnav>hao123</a> <a href=http://map.baidu.com name=tj_trmap class=mnav>地图</a> <a href=http://v.baidu.com name=tj_trvideo class=mnav>视频</a> <a href=http://tieba.baidu.com name=tj_trtieba class=mnav>贴吧</a> <noscript> <a href=http://www.baidu.com/bdorz/login.gif?login&tpl=mn&u=http%3A%2F%2Fwww.baidu.com%2f%3fbdorz_come%3d1 name=tj_login class=lb>登录</a> </noscript> <script>document.write('<a href="http://www.baidu.com/bdorz/login.gif?login&tpl=mn&u='+ encodeURIComponent(window.location.href+ (window.location.search === "" ? "?" : "&")+ "bdorz_come=1")+ '" name="tj_login" class="lb">登录</a>'); </script> <a href=//www.baidu.com/more/ name=tj_briicon class=bri style="display: block;">更多产品</a> </div> </div> </div> <div id=ftCon> <div id=ftConw> <p id=lh> <a href=http://home.baidu.com>关于百度</a> <a href=http://ir.baidu.com>About Baidu</a> </p> <p id=cp>©2017 Baidu <a href=http://www.baidu.com/duty/>使用百度前必读</a> <a href=http://jianyi.baidu.com/ class=cp-feedback>意见反馈</a> 京ICP证030173号 <img src=//www.baidu.com/img/gs.gif> </p> </div> </div> </div> </body> </html>
三、发送Get无参请求
public class HttpClientTest { /** * 使用HttpClient发送Get请求 */ @Test public void testGet() { CloseableHttpClient aDefault = HttpClients.createDefault(); // 输入url地址 //构造httpGet请求对象 HttpGet httpGet = new HttpGet("https://www.baidu.com/"); //可关闭的响应 CloseableHttpResponse response = null; try { response = aDefault.execute(httpGet); //获取响应结果:DecompressingEntity HttpEntity entity = response.getEntity(); //对HttpEntity进行操作 String s = EntityUtils.toString(entity, StandardCharsets.UTF_8); System.out.println(s); //确保流关闭 EntityUtils.consume(entity); } catch (Exception e) { e.printStackTrace(); } finally { if (aDefault != null) { try { aDefault.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } } }
运行结果同上
-保存网络图片到本地
public void test2() throws Exception{ CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); String urlStr="https://pics5.baidu.com/feed/c9fcc3cec3fdfc03f254ca734915349ea5c22685.png?token=3c875fd7c636738571cee9df4199e80c"; HttpGet httpGet=new HttpGet(urlStr); //可关闭的响应 CloseableHttpResponse response=null; try { response=closeableHttpClient.execute(httpGet); HttpEntity entity = response.getEntity(); //image/jpg image/jpeg image/png image 图片的后缀 String contentType = entity.getContentType().getValue(); String suffix=".jpg"; if (contentType.contains("jpg")||contentType.contains("jpeg")){ suffix=".jpg"; } else if (contentType.contains("bmp")||contentType.contains("bitmap")) { suffix=".bmp"; } else if (contentType.contains("png")) { suffix=".png"; } else if (contentType.contains("gif")) { suffix=".gif"; } //获取文件的字节流 byte[] bytes = EntityUtils.toByteArray(entity); String localAbsPath="E:\\CloudMusic\\abc"+suffix; FileOutputStream fos=new FileOutputStream(localAbsPath); fos.write(bytes); fos.close(); } catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
-设置访问代理
/** * 设置访问代理 */ @Test public void test3() throws Exception{ CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); String urlStr="https://www.baidu.com/"; HttpGet httpGet=new HttpGet(urlStr); //创建一个代理 String ip="195.53.49.11"; int port=3128; HttpHost proxy= new HttpHost(ip,port); //对每一个请求进行配置,会覆盖全局默认请求配置 RequestConfig requestConfig = RequestConfig.custom().setProxy(proxy).build(); httpGet.setConfig(requestConfig); CloseableHttpResponse response=null; try { response=closeableHttpClient.execute(httpGet); HttpEntity entity = response.getEntity(); String toStringResult = EntityUtils.toString(entity); EntityUtils.consume(entity); }catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
-设置连接超时时间
/** * 设置链接超时时间 * */ @Test public void test4() throws Exception{ CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); String urlStr="https://www.github.com//"; HttpGet httpGet=new HttpGet(urlStr); //创建一个代理 String ip="195.53.49.11"; int port=3128; HttpHost proxy= new HttpHost(ip,port); //对每一个请求进行配置,会覆盖全局默认请求配置 RequestConfig requestConfig = RequestConfig .custom() //超时时间,ms为单位 完成tcp3次握手 的时间上限 .setConnectTimeout(5000) //读取超时,ms为单位,表示从请求的网址处获得响应数据的时间间隔 .setSocketTimeout(3000) //从连接池里获取connection的超时时间 .setConnectionRequestTimeout(5000) .build(); httpGet.setConfig(requestConfig); CloseableHttpResponse response=null; try { response=closeableHttpClient.execute(httpGet); HttpEntity entity = response.getEntity(); String toStringResult = EntityUtils.toString(entity); EntityUtils.consume(entity); }catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
四、发送Get带参数请求
/** * httpGet有参请求 * * @throws Exception */ @Test public void HttpClientParamTest() throws Exception { //创建HttpClients对象 CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); //设置请求地址 //创建urlBuilder URIBuilder uriBuilder=new URIBuilder("http://yun.itheima.com/search"); //设置参数 uriBuilder.setParameter("keys","Java"); //HttpGet对象 设置url访问地址 HttpGet httpGet = new HttpGet(uriBuilder.build()); System.out.println("发送请求信息"+httpGet); CloseableHttpResponse response = null; try { response = closeableHttpClient.execute(httpGet); //解析响应 if (response.getStatusLine().getStatusCode() == 200) { String content = EntityUtils.toString(response.getEntity(), "utf-8"); System.out.println(content.length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } }
五、post无参数请求
/** * httpPost 无参数请 * * @throws Exception */ @Test public void HttpClientPostTest() throws Exception { //创建HttpClients对象 CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); //HttpPost对象 设置url访问地址 HttpPost httpPost = new HttpPost(); CloseableHttpResponse response = null; try { response = closeableHttpClient.execute(httpPost); //解析响应 if (response.getStatusLine().getStatusCode() == 200) { String content = EntityUtils.toString(response.getEntity(), "utf-8"); System.out.println(content.length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
六、post有参请求
/** * httpPost 带参数请求 * * @throws Exception */ @Test public void HttpClientPostParamTest() throws Exception { //创建HttpClients对象 CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); //HttpPost对象 设置url访问地址 HttpPost httpPost = new HttpPost("http://yun.itheima.com/search"); //声明list集合,封装表单中的参数 List<NameValuePair> params = new ArrayList<NameValuePair>(); //设置请求地址:http://yun.itheima.com/search?keys=Java params.add(new BasicNameValuePair("keys", "java")); //创建表单的Entity对象 UrlEncodedFormEntity formEntity = new UrlEncodedFormEntity(params, "utf-8"); //设置表单的Entity对象到post请求中 httpPost.setEntity(formEntity); CloseableHttpResponse response = null; try { response = closeableHttpClient.execute(httpPost); //解析响应 if (response.getStatusLine().getStatusCode() == 200) { String content = EntityUtils.toString(response.getEntity(), "utf-8"); System.out.println(content.length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
七、连接池
-若每次请求都要创建HttpClient会有频繁创建和销毁问题,可以使用连接池来解决
/** * 连接池管理HttpClient * * @throws Exception */ @Test public void HttpClientPoolTest() { //创建连接池管理器 PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(); //设置最大链接数 cm.setMaxTotal(100); //设置每个主机最大连接数 cm.setDefaultMaxPerRoute(10); //使用连接池管理器发送请求 doGet(cm); doGet(cm); } private void doGet(PoolingHttpClientConnectionManager cm) { //不会每次创建新的HttpClient,而是从连接池中获取HttpClient对象 CloseableHttpClient httpClient = HttpClients.custom().setConnectionManager(cm).build(); HttpGet httpGet = new HttpGet("http://www.itcast.cn"); CloseableHttpResponse response = null; try { response = httpClient.execute(httpGet); if (response.getStatusLine().getStatusCode() == 200) { String content = EntityUtils.toString(response.getEntity()); System.out.println(content.length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } //不能关闭HttpClient // httpClient.close(); } } }
八、HttpClient请求参数
/** * HttpClient 请求参数 */ @Test public void HttpClientConfigTest() { //创建HttpClients对象 CloseableHttpClient closeableHttpClient = HttpClients.createDefault(); //HttpPost对象 设置url访问地址 HttpGet httpGet = new HttpGet("http://www.itcast.cn"); //配置请求信息 RequestConfig config=RequestConfig .custom() .setConnectionRequestTimeout(1000) //创建链接的最长时间,单位是毫秒 .setConnectionRequestTimeout(500) //设置获取链接最长时间 .setSocketTimeout(10*1000) //设置数据传输的最长时间 .build(); //设置请求信息 httpGet.setConfig(config); CloseableHttpResponse response = null; try { response = closeableHttpClient.execute(httpGet); //解析响应 if (response.getStatusLine().getStatusCode() == 200) { String content = EntityUtils.toString(response.getEntity(), "utf-8"); System.out.println(content.length()); } } catch (Exception e) { e.printStackTrace(); } finally { if (closeableHttpClient != null) { try { closeableHttpClient.close(); } catch (IOException e) { e.printStackTrace(); } } if (response != null) { try { response.close(); } catch (IOException e) { e.printStackTrace(); } } } }
浙公网安备 33010602011771号