假如你现在还在为自己的技术担忧,假如你现在想提升自己的工资,假如你想在职场上获得更多的话语权,假如你想顺利的度过35岁这个魔咒,假如你想体验BAT的工作环境,那么现在请我们一起开启提升技术之旅吧,详情请点击
一,httpclient的理解
httpcliet就是模仿浏览器在服务器内部从一个项目调用另一个项目的技术。比如说调用接口等。
HttpClient 是 Apache Jakarta Common 下的子项目,用来提供高效的、最新的、功能丰富的支持 HTTP 协议的客户端编程工具包,并且它支持 HTTP 协议最新的版本和建议。
二,httpclient的使用方法
1.1,jar包
需要把httpclient的jar包添加到工程中。只需要在工程中添加httpclient的依赖。
1.2,使用方法
1.2.1,get无参请求
1 @Test 2 public void doGet() throws Exception { 3 //创建一个httpclient对象 4 CloseableHttpClient httpClient = HttpClients.createDefault(); 5 //创建一个GET对象 6 HttpGet get = new HttpGet("http://www.sogou.com"); 7 //执行请求 8 CloseableHttpResponse response = httpClient.execute(get); 9 //取响应的结果10 int statusCode = response.getStatusLine().getStatusCode();11 System.out.println(statusCode);12 HttpEntity entity = response.getEntity();13 String string = EntityUtils.toString(entity, "utf-8");14 System.out.println(string);15 //关闭httpclient16 response.close();17 httpClient.close();18 }
1.2.2,get带参请求
1 @Test 2 public void doGetWithParam() throws Exception{ 3 //创建一个httpclient对象 4 CloseableHttpClient httpClient = HttpClients.createDefault(); 5 //创建一个uri对象 6 URIBuilder uriBuilder = new URIBuilder("http://www.sogou.com/web"); 7 uriBuilder.addParameter("query", "花千骨"); 8 HttpGet get = new HttpGet(uriBuilder.build()); 9 //执行请求10 CloseableHttpResponse response = httpClient.execute(get);11 //取响应的结果12 int statusCode = response.getStatusLine().getStatusCode();13 System.out.println(statusCode);14 HttpEntity entity = response.getEntity();15 String string = EntityUtils.toString(entity, "utf-8");16 System.out.println(string);17 //关闭httpclient18 response.close();19 httpClient.close();20 }
1.2.3,post无参请求
1 @Test 2 public void doPost() throws Exception { 3 CloseableHttpClient httpClient = HttpClients.createDefault(); 4 5 //创建一个post对象 6 HttpPost post = new HttpPost("http://localhost:8082/httpclient/post.action"); 7 //执行post请求 8 CloseableHttpResponse response = httpClient.execute(post); 9 String string = EntityUtils.toString(response.getEntity());10 System.out.println(string);11 response.close();12 httpClient.close();13 14 }
1.2.4,post带参请求
1 @Test 2 public void doPostWithParam() throws Exception{ 3 CloseableHttpClient httpClient = HttpClients.createDefault(); 4 5 //创建一个post对象 6 HttpPost post = new HttpPost("http://localhost:8082/httpclient/post.action"); 7 //创建一个Entity。模拟一个表单 8 ListkvList = new ArrayList<>(); 9 kvList.add(new BasicNameValuePair("username", "张三"));10 kvList.add(new BasicNameValuePair("password", "123"));11 12 //包装成一个Entity对象 13 StringEntity entity = new UrlEncodedFormEntity(kvList, "utf-8");14 //设置请求的内容 15 post.setEntity(entity);16 17 //执行post请求18 CloseableHttpResponse response = httpClient.execute(post);19 String string = EntityUtils.toString(response.getEntity());20 System.out.println(string);21 response.close();22 httpClient.close();23 }
三,httpclient的案例讲解
3.1,httpclient的工具类httpclientutil
1 package com.http; 2 3 import java.io.ByteArrayOutputStream; 4 import java.io.EOFException; 5 import java.io.IOException; 6 import java.io.InputStream; 7 import java.io.InterruptedIOException; 8 import java.io.UnsupportedEncodingException; 9 import java.net.SocketException; 10 import java.net.URI; 11 import java.net.URISyntaxException; 12 import java.net.UnknownHostException; 13 import java.security.KeyManagementException; 14 import java.security.NoSuchAlgorithmException; 15 import java.security.cert.X509Certificate; 16 import java.util.ArrayList; 17 import java.util.List; 18 import java.util.Map; 19 import java.util.Map.Entry; 20 import java.util.regex.Matcher; 21 import java.util.regex.Pattern; 22 import java.util.zip.GZIPInputStream; 23 24 import javax.net.ssl.SSLContext; 25 import javax.net.ssl.SSLException; 26 import javax.net.ssl.SSLHandshakeException; 27 import javax.net.ssl.TrustManager; 28 import javax.net.ssl.X509TrustManager; 29 30 import org.apache.commons.io.IOUtils; 31 import org.apache.commons.lang3.StringUtils; 32 import org.apache.http.Header; 33 import org.apache.http.HttpEntity; 34 import org.apache.http.HttpEntityEnclosingRequest; 35 import org.apache.http.HttpHost; 36 import org.apache.http.HttpRequest; 37 import org.apache.http.HttpResponse; 38 import org.apache.http.NameValuePair; 39 import org.apache.http.NoHttpResponseException; 40 import org.apache.http.ParseException; 41 import org.apache.http.ProtocolException; 42 import org.apache.http.client.ClientProtocolException; 43 import org.apache.http.client.CookieStore; 44 import org.apache.http.client.HttpRequestRetryHandler; 45 import org.apache.http.client.config.CookieSpecs; 46 import org.apache.http.client.config.RequestConfig; 47 import org.apache.http.client.config.RequestConfig.Builder; 48 import org.apache.http.client.entity.UrlEncodedFormEntity; 49 import org.apache.http.client.methods.CloseableHttpResponse; 50 import org.apache.http.client.methods.HttpGet; 51 import org.apache.http.client.methods.HttpPost; 52 import org.apache.http.client.protocol.HttpClientContext; 53 import org.apache.http.conn.ConnectTimeoutException; 54 import org.apache.http.conn.HttpHostConnectException; 55 import org.apache.http.conn.ssl.SSLConnectionSocketFactory; 56 import org.apache.http.cookie.Cookie; 57 import org.apache.http.entity.ByteArrayEntity; 58 import org.apache.http.impl.client.BasicCookieStore; 59 import org.apache.http.impl.client.CloseableHttpClient; 60 import org.apache.http.impl.client.DefaultRedirectStrategy; 61 import org.apache.http.impl.client.HttpClientBuilder; 62 import org.apache.http.impl.client.HttpClients; 63 import org.apache.http.impl.conn.PoolingHttpClientConnectionManager; 64 import org.apache.http.message.BasicNameValuePair; 65 import org.apache.http.protocol.HttpContext; 66 import org.apache.http.util.ByteArrayBuffer; 67 import org.apache.http.util.EntityUtils; 68 69 /** 70 * HttpClient工具封装类,Post,Get请求,代理请求 71 * 作者: 72 * 版本:1.0 73 * 创建日期:下午9:21:00 74 */ 75 public class HttpClientUtil { 76 77 /***连接超时时间*/ 78 private Integer connectTimeout =60*1000; 79 80 private Integer socketTimeout =180*1000; 81 private CloseableHttpClient httpClient = null; 82 83 private CookieStore cookieStore = new BasicCookieStore(); 84 85 86 /** 代理请求 */ 87 public HttpClientUtil(String proxyHost, int proxyPort) { 88 this(proxyHost, proxyPort, -1, -1, 0, 0, true); 89 } 90 91 /** 默认*/ 92 public HttpClientUtil() { 93 this(null, 0, -1, -1, 0, 0, true); 94 } 95 96 /** 进行请求无代理设置连接时间 */ 97 public HttpClientUtil(int socketTimeout, int connectTimeout) { 98 this(null, 0, socketTimeout, connectTimeout, 0, 0, true); 99 }100 101 102 /**103 * 104 * @param proxyHost 代理主机地址105 * @param proxyPort 代理端口106 * @param socketTimeout107 * @param connectTimeout108 * @param route 109 * @param maxTotal110 * @param followRedirect111 */112 public HttpClientUtil(String proxyHost, int proxyPort, int socketTimeout, int connectTimeout, int route, int maxTotal, boolean followRedirect){113 Builder builder = RequestConfig.custom();114 builder.setCookieSpec(CookieSpecs.BROWSER_COMPATIBILITY);115 if (followRedirect) {116 builder.setCircularRedirectsAllowed(true);117 builder.setMaxRedirects(100);118 }119 if (StringUtils.isNotBlank(proxyHost) && proxyPort > 0) {120 builder.setProxy(new HttpHost(proxyHost, proxyPort));121 }122 123 //设置连接时间124 if (socketTimeout != -1) {125 this.socketTimeout = socketTimeout;126 }127 builder.setSocketTimeout(this.socketTimeout);128 129 if (connectTimeout != -1) {130 this.connectTimeout = connectTimeout;131 }132 builder.setConnectTimeout(this.connectTimeout);133 builder.setConnectionRequestTimeout(this.connectTimeout);134 135 RequestConfig requestConfig = builder.build();136 init(requestConfig, route, maxTotal);137 }138 139 private void init(RequestConfig requestConfig, int route, int maxTotal) {140 X509TrustManager x509mgr = new X509TrustManager() {141 @Override142 public void checkClientTrusted(X509Certificate[] xcs, String string) {143 }144 145 @Override146 public void checkServerTrusted(X509Certificate[] xcs, String string) {147 }148 149 @Override150 public X509Certificate[] getAcceptedIssuers() {151 return null;152 }153 };154 155 SSLContext sslContext = null;156 try {157 sslContext = SSLContext.getInstance("TLS");158 } catch (NoSuchAlgorithmException e1) {159 e1.printStackTrace();160 }161 162 try {163 sslContext.init(null, new TrustManager[] { x509mgr }, null);164 } catch (KeyManagementException e) {165 e.printStackTrace();166 }167 168 SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslContext, SSLConnectionSocketFactory.ALLOW_ALL_HOSTNAME_VERIFIER);169 170 HttpRequestRetryHandler httpRequestRetryHandler = new HttpRequestRetryHandler() {171 @Override172 public boolean retryRequest(IOException exception, int executionCount, HttpContext context) {173 if (executionCount >= 5) { // 如果已经重试了5次,就放弃174 return false;175 }176 if (exception instanceof NoHttpResponseException) { // 如果服务器丢掉了连接,那么就重试177 return true;178 }179 if (exception instanceof SSLHandshakeException) { // 不要重试SSL握手异常180 return false;181 }182 if (exception instanceof InterruptedIOException) { // 超时183 return false;184 }185 if (exception instanceof UnknownHostException) { // 目标服务器不可达186 return false;187 }188 if (exception instanceof ConnectTimeoutException) { // 连接被拒绝189 return false;190 }191 if (exception instanceof SSLException) { // ssl握手异常192 return false;193 }194 // 2016-03-09针对broken pipe的问题做处理195 if (exception instanceof SocketException) {196 return true;197 }198 199 HttpClientContext clientContext = HttpClientContext.adapt(context);200 HttpRequest request = clientContext.getRequest();201 // 如果请求是幂等的,就再次尝试202 if (!(request instanceof HttpEntityEnclosingRequest)) {203 return true;204 }205 return false;206 }207 };208 DefaultRedirectStrategy redirectStrategy = new DefaultRedirectStrategy() {209 public boolean isRedirected(HttpRequest request, HttpResponse response, HttpContext context) {210 boolean isRedirect = false;211 try {212 isRedirect = super.isRedirected(request, response, context);213 } catch (ProtocolException e) {214 e.printStackTrace();215 }216 if (!isRedirect) {217 int responseCode = response.getStatusLine().getStatusCode();218 if (responseCode == 301 || responseCode == 302) {219 return true;220 }221 }222 return isRedirect;223 }224 225 @Override226 protected URI createLocationURI(String location) throws ProtocolException {227 location = location.replace("|", "%7C");228 return super.createLocationURI(location);229 }230 };231 232 HttpClientBuilder httpClientBuilder = HttpClients.custom();233 httpClientBuilder.setDefaultRequestConfig(requestConfig);234 if (route > 0 && maxTotal > 0) {235 PoolingHttpClientConnectionManager connManager = new PoolingHttpClientConnectionManager();236 connManager.setDefaultMaxPerRoute(route);237 connManager.setMaxTotal(maxTotal);238 httpClientBuilder.setConnectionManager(connManager);239 }240 241 httpClientBuilder.setSSLSocketFactory(sslsf);242 httpClientBuilder.setDefaultCookieStore(cookieStore);243 httpClientBuilder.setRedirectStrategy(redirectStrategy);244 httpClientBuilder.setRetryHandler(httpRequestRetryHandler);245 httpClient = httpClientBuilder.build();246 }247 public Response sendRequest(Request request) throws Exception {248 // request.setHeader("Accept",249 // "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8");250 // request.setHeader("Accept-Encoding", "gzip, deflate");251 if (request.getHeader("User-Agent") == null) {252 request.setHeader("User-Agent", "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.8; rv:24.0) Gecko/20100101 Firefox/24.0");253 }254 request.setHeader("Accept-Language", "zh-cn,zh;q=0.8,en-us;q=0.5,en;q=0.3");255 request.setHeader("Connection", "keep-alive");256 257 // logger.debug("发送请求:" + request);258 259 String method = request.getProperty("method").toLowerCase();260 String url = request.getProperty("url");261 Mapheaders = request.getHeaders();262 Map params = request.getParams();263 264 List formParams = new ArrayList ();265 if (params != null && params.size() != 0) {266 formParams = new ArrayList ();267 for (Entry entry : params.entrySet()) {268 formParams.add(new BasicNameValuePair(entry.getKey(), entry.getValue()));269 }270 }271 272 Response response = null;273 if ("post".equals(method)) {274 byte[] postData = request.getPostData();275 if (postData != null) {276 response = post(url, postData, headers);277 } else {278 response = post(url, formParams, headers);279 }280 } else if ("get".equals(method)) {281 response = get(url, formParams, headers);282 }283 return response;284 }285 286 /**287 * Get请求288 * 289 * @param url290 * @param params291 * @return292 */293 public Response get(String url, List params, Map headers) {294 Response response = new Response();295 try {296 // Get请求297 HttpGet httpGet = new HttpGet(url);298 299 String encoding = "utf-8";300 301 // 设置头302 if (headers != null && headers.size() != 0) {303 for (Entry entry : headers.entrySet()) {304 httpGet.setHeader(entry.getKey(), entry.getValue());305 }306 307 String contentType = headers.get("Content-Type");308 if (StringUtils.isNotBlank(contentType)) {309 if (matcher(contentType, "(charset)\\s?=\\s?(gbk)")) {310 encoding = "gbk";311 } else if (matcher(contentType, "(charset)\\s?=\\s?(gb2312)")) {312 encoding = "gb2312";313 }314 }315 }316 317 // 设置参数,如果url上已经有了问号,就不附加参数318 if (params != null && params.size() > 0) {319 if (httpGet.getURI().toString().indexOf("?") == -1) {320 String str = EntityUtils.toString(new UrlEncodedFormEntity(params, encoding));321 httpGet.setURI(new URI(httpGet.getURI().toString() + "?" + str));322 } else {323 String str = EntityUtils.toString(new UrlEncodedFormEntity(params, encoding));324 httpGet.setURI(new URI(httpGet.getURI().toString() + "&" + str));325 }326 }327 328 // 发送请求329 CloseableHttpResponse httpResponse = httpClient.execute(httpGet);330 331 try {332 int statusCode = httpResponse.getStatusLine().getStatusCode();333 response.setStatusCode(statusCode);334 ByteArrayOutputStream byteOut = new ByteArrayOutputStream();335 // 获取返回数据336 HttpEntity entity = httpResponse.getEntity();337 338 Header[] responseHeaders = httpResponse.getAllHeaders();339 for (Header header : responseHeaders) {340 response.setHeader(header.getName(), header.getValue());341 }342 343 Header header = entity.getContentEncoding();344 if (header != null && header.getValue().toLowerCase().equals("gzip")) {345 byte[] bytes = IOUtils.toByteArray(new GZIPInputStream(entity.getContent()));346 response.setContent(bytes);347 } else {348 byte[] bytes = getData(entity);349 response.setContent(bytes);350 }351 return response;352 } finally {353 httpResponse.close();354 }355 } catch (ConnectTimeoutException e) {356 } catch (HttpHostConnectException e) {357 } catch (ParseException e) {358 } catch (UnsupportedEncodingException e) {359 } catch (IOException e) {360 } catch (URISyntaxException e) {361 } catch (Exception e) {362 }363 return null;364 }365 366 /**367 * // Post请求368 * 369 * @param url370 * @param params371 * @return372 */373 public Response post(String url, byte[] data, Map headers) {374 Response response = new Response();375 try {376 // Post请求377 HttpPost httpPost = new HttpPost(url);378 // 设置头379 if (headers != null && headers.size() != 0) {380 for (Entry entry : headers.entrySet()) {381 httpPost.setHeader(entry.getKey(), entry.getValue());382 }383 }384 385 // 设置参数386 httpPost.setEntity(new ByteArrayEntity(data));387 388 // 发送请求389 CloseableHttpResponse httpResponse = httpClient.execute(httpPost);390 391 try {392 int statusCode = httpResponse.getStatusLine().getStatusCode();393 response.setStatusCode(statusCode);394 395 // 获取返回数据396 HttpEntity entity = httpResponse.getEntity();397 398 Header header = entity.getContentEncoding();399 if (header != null && header.getValue().toLowerCase().equals("gzip")) {400 byte[] bytes = IOUtils.toByteArray(new GZIPInputStream(entity.getContent()));401 response.setContent(bytes);402 } else {403 byte[] bytes = EntityUtils.toByteArray(entity);404 response.setContent(bytes);405 }406 407 return response;408 } finally {409 httpResponse.close();410 }411 } catch (ConnectTimeoutException e) {412 } catch (HttpHostConnectException e) {413 } catch (UnsupportedEncodingException e) {414 } catch (ClientProtocolException e) {415 } catch (ParseException e) {416 } catch (IOException e) {417 } catch (Exception e) {418 }419 return null;420 }421 private byte[] getData(HttpEntity entity) throws IOException {422 if (entity == null) {423 throw new IllegalArgumentException("HTTP entity may not be null");424 }425 InputStream inputStream = entity.getContent();426 if (inputStream == null) {427 return null;428 }429 try {430 if (entity.getContentLength() > Integer.MAX_VALUE) {431 throw new IllegalArgumentException("HTTP entity too large to be buffered in memory");432 }433 int i = (int) entity.getContentLength();434 if (i < 0) {435 i = 4096;436 }437 438 ByteArrayBuffer buffer = new ByteArrayBuffer(i);439 byte[] tmp = new byte[1024];440 int l = -1;441 try {442 while ((l = inputStream.read(tmp)) != -1) {443 buffer.append(tmp, 0, l);444 }445 } catch (EOFException e) {446 buffer.clear();447 // 针对于以没有结束符的做fix处理,减小缓存,并进行异常处理,忽略最后不能获取的数据448 tmp = new byte[32];449 try {450 while ((l = inputStream.read(tmp)) != 1) {451 buffer.append(tmp, 0, l);452 }453 } catch (EOFException e2) {454 }455 456 }457 // TODO 查明具体没有返回的原因458 byte[] byteArray = buffer.toByteArray();459 if (byteArray == null || byteArray.length == 0) {460 return buffer.buffer();461 }462 return byteArray;463 } finally {464 inputStream.close();465 }466 }467 /**468 * // Post请求469 * 470 * @param url471 * @param params472 * @return473 */474 public Response post(String url, List params, Map headers) {475 Response response = new Response();476 try {477 // Post请求478 HttpPost httpPost = new HttpPost(url);479 480 String encoding = "utf-8";481 482 // 设置头483 if (headers != null && headers.size() != 0) {484 for (Entry entry : headers.entrySet()) {485 httpPost.setHeader(entry.getKey(), entry.getValue());486 }487 488 String contentType = headers.get("Content-Type");489 if (StringUtils.isNotBlank(contentType)) {490 if (matcher(contentType, "(charset)\\s?=\\s?(gbk)")) {491 encoding = "gbk";492 } else if (matcher(contentType, "(charset)\\s?=\\s?(gb2312)")) {493 encoding = "gb2312";494 }495 }496 }497 498 // 设置参数499 if (params != null && params.size() > 0) {500 httpPost.setEntity(new UrlEncodedFormEntity(params, encoding));501 }502 503 // 发送请求504 CloseableHttpResponse httpResponse = httpClient.execute(httpPost);505 506 try {507 int statusCode = httpResponse.getStatusLine().getStatusCode();508 response.setStatusCode(statusCode);509 510 // 获取返回数据511 HttpEntity entity = httpResponse.getEntity();512 513 Header header = entity.getContentEncoding();514 if (header != null && header.getValue().toLowerCase().equals("gzip")) {515 byte[] data = IOUtils.toByteArray(new GZIPInputStream(entity.getContent()));516 response.setContent(data);517 } else {518 byte[] data = getData(entity);519 response.setContent(data);520 }521 522 return response;523 } finally {524 httpResponse.close();525 }526 } catch (ConnectTimeoutException e) {527 } catch (HttpHostConnectException e) {528 } catch (UnsupportedEncodingException e) {529 } catch (ClientProtocolException e) {530 } catch (ParseException e) {531 } catch (IOException e) {532 } catch (Exception e) {533 }534 return null;535 }536 537 /**538 * 获取Response内容字符集539 * 540 * @param response541 * @return542 */543 public String getContentCharset(HttpResponse response) {544 String charset = "ISO_8859-1";545 Header header = response.getEntity().getContentType();546 if (header != null) {547 String s = header.getValue();548 if (matcher(s, "(charset)\\s?=\\s?(utf-?8)")) {549 charset = "utf-8";550 } else if (matcher(s, "(charset)\\s?=\\s?(gbk)")) {551 charset = "gbk";552 } else if (matcher(s, "(charset)\\s?=\\s?(gb2312)")) {553 charset = "gb2312";554 }555 }556 557 Header encoding = response.getEntity().getContentEncoding();558 559 return charset;560 }561 562 /**563 * 正则匹配564 * 565 * @param s566 * @param pattern567 * @return568 */569 private boolean matcher(String s, String pattern) {570 Pattern p = Pattern.compile(pattern, Pattern.CASE_INSENSITIVE + Pattern.UNICODE_CASE);571 Matcher matcher = p.matcher(s);572 if (matcher.find()) {573 return true;574 } else {575 return false;576 }577 }578 579 public Integer getConnectTimeout() {580 return connectTimeout;581 }582 583 public void setConnectTimeout(Integer connectTimeout) {584 this.connectTimeout = connectTimeout;585 }586 587 public Integer getSocketTimeout() {588 return socketTimeout;589 }590 591 public void setSocketTimeout(Integer socketTimeout) {592 this.socketTimeout = socketTimeout;593 }594 595 public CloseableHttpClient getHttpClient() {596 return httpClient;597 }598 599 public void setHttpClient(CloseableHttpClient httpClient) {600 this.httpClient = httpClient;601 }602 603 public CookieStore getCookieStore() {604 return cookieStore;605 }606 607 public void setCookieStore(CookieStore cookieStore) {608 for(Cookie cookie:cookieStore.getCookies()){609 this.cookieStore.addCookie(cookie);610 }611 }612 613 }
3.2, resource的property的文件
1 REST_BASE_URL=http://192.168.25.136:8080/rest2 REST_INDEX_AD_URL=/content/list/89
3.3,类中的调用
1 public class ContentServiceImpl implements ContentService { 2 3 @Value("${REST_BASE_URL}") 4 private String REST_BASE_URL; 5 @Value("${REST_INDEX_AD_URL}") 6 private String REST_INDEX_AD_URL; 7 8 @Override 9 public String getContentList() {10 //调用服务层的服务11 String result = HttpClientUtil.doGet(REST_BASE_URL + REST_INDEX_AD_URL);12 //把字符串转换成TaotaoResult13 try {14 TaotaoResult taotaoResult = TaotaoResult.formatToList(result, TbContent.class);15 //取内容列表16 Listlist = (List ) taotaoResult.getData();17 List