HttpClient库设置超时
HttpClient庫(kù)API跟Lucene一樣,每個(gè)版本的API都變化很大,這有點(diǎn)讓人頭疼。就好比創(chuàng)建一個(gè)HttpClient對(duì)象吧,每一個(gè)版本的都不一樣。
3.X是正常的Java語(yǔ)法
HttpClient httpClient=new DefaultHttpClient();
4.3變成了工廠(chǎng)模式
CloseableHttpClient httpClient = HttpClients.createDefault();
超時(shí)設(shè)置方法
3.x HttpClient client = new HttpClient(); client.setConnectionTimeout(30000); client.setTimeout(30000);HttpClient httpClient= new HttpClient(); httpClient.getHttpConnectionManager().getParams().setConnectionTimeout(5000);4.1 HttpClient httpClient=newDefaultHttpClient(); httpClient.getParams().setParameter(CoreConnectionPNames.CONNECTION_TIMEOUT,2000);//連接時(shí)間 httpClient.getParams().setParameter(CoreConnectionPNames.SO_TIMEOUT,2000);//數(shù)據(jù)傳輸時(shí)間4.3 CloseableHttpClient httpClient = HttpClients.createDefault(); HttpGet httpGet=newHttpGet("http://www.baidu.com");//HTTP Get請(qǐng)求(POST雷同) RequestConfig requestConfig = RequestConfig.custom().setSocketTimeout(2000).setConnectTimeout(2000).build();//設(shè)置請(qǐng)求和傳輸超時(shí)時(shí)間 httpGet.setConfig(requestConfig); httpClient.execute(httpGet);//執(zhí)行請(qǐng)求從設(shè)置時(shí)間上來(lái)看,4.3之前的是一類(lèi),都是一個(gè)HttpClient綁定好一套配置。
4.3之后,HttpClient不再提供時(shí)間配置參數(shù),而是每一種請(qǐng)求對(duì)應(yīng)一套配置。
BTW,4.3版本不設(shè)置超時(shí)的話(huà),一旦服務(wù)器沒(méi)有響應(yīng),等待時(shí)間N久(>24小時(shí))。
HttpClient升級(jí)到4.5版本后,API有很多變化,HttpClient 4之后,API一直沒(méi)有太穩(wěn)定,我感覺(jué)4.5版本抽象后,很多API應(yīng)該快穩(wěn)定了。
使用HttpClient,一般都需要設(shè)置連接超時(shí)時(shí)間和獲取數(shù)據(jù)超時(shí)時(shí)間。這兩個(gè)參數(shù)很重要,目的是為了防止訪(fǎng)問(wèn)其他http時(shí),由于超時(shí)導(dǎo)致自己的應(yīng)用受影響。
4.5版本中,這兩個(gè)參數(shù)的設(shè)置都抽象到了RequestConfig中,由相應(yīng)的Builder構(gòu)建,具體的例子如下:
CloseableHttpClient httpclient = HttpClients.createDefault(); HttpGet httpGet = new HttpGet("http://stackoverflow.com/"); RequestConfig requestConfig = RequestConfig.custom() .setConnectTimeout(5000).setConnectionRequestTimeout(1000) .setSocketTimeout(5000).build(); httpGet.setConfig(requestConfig); CloseableHttpResponse response = httpclient.execute(httpGet); System.out.println("得到的結(jié)果:" + response.getStatusLine());//得到請(qǐng)求結(jié)果 HttpEntity entity = response.getEntity();//得到請(qǐng)求回來(lái)的數(shù)據(jù)setConnectTimeout:設(shè)置連接超時(shí)時(shí)間,單位毫秒。
setConnectionRequestTimeout:設(shè)置從connect Manager(連接池)獲取Connection 超時(shí)時(shí)間,單位毫秒。這個(gè)屬性是新加的屬性,因?yàn)槟壳鞍姹臼强梢怨蚕磉B接池的。
setSocketTimeout:請(qǐng)求獲取數(shù)據(jù)的超時(shí)時(shí)間(即響應(yīng)時(shí)間),單位毫秒。 如果訪(fǎng)問(wèn)一個(gè)接口,多少時(shí)間內(nèi)無(wú)法返回?cái)?shù)據(jù),就直接放棄此次調(diào)用。
HttpClient內(nèi)部有三個(gè)超時(shí)時(shí)間設(shè)置:連接池獲取可用連接超時(shí),連接超時(shí),讀取數(shù)據(jù)超時(shí)
先看以下HttpClient的初始化代碼:
RequestConfig requestConfig = RequestConfig.custom() .setConnectionRequestTimeout(config.connReqTimeout) //從連接池中獲取連接的超時(shí)時(shí)間 //與服務(wù)器連接超時(shí)時(shí)間:httpclient會(huì)創(chuàng)建一個(gè)異步線(xiàn)程用以創(chuàng)建socket連接,此處設(shè)置該socket的連接超時(shí)時(shí)間 .setConnectTimeout(config.connTimeout) .setSocketTimeout(config.socketTimeout) //socket讀數(shù)據(jù)超時(shí)時(shí)間:從服務(wù)器獲取響應(yīng)數(shù)據(jù)的超時(shí)時(shí)間 .build(); httpClient = HttpClientBuilder.create() .setMaxConnTotal(config.maxConnTotal) //連接池中最大連接數(shù) /** * 分配給同一個(gè)route(路由)最大的并發(fā)連接數(shù)。 * route:運(yùn)行環(huán)境機(jī)器 到 目標(biāo)機(jī)器的一條線(xiàn)路。 * 舉例來(lái)說(shuō),我們使用HttpClient的實(shí)現(xiàn)來(lái)分別請(qǐng)求 www.baidu.com 的資源和 www.bing.com 的資源那么他就會(huì)產(chǎn)生兩個(gè)route。 */ .setMaxConnPerRoute(config.maxConnPerRoute) .setDefaultRequestConfig(requestConfig) .build();三個(gè)超時(shí)時(shí)間詳解:
1.從連接池中獲取可用連接超時(shí)
HttpClient中的要用連接時(shí)嘗試從連接池中獲取,若是在等待了一定的時(shí)間后還沒(méi)有獲取到可用連接(比如連接池中沒(méi)有空閑連接了)
則會(huì)拋出獲取連接超時(shí)異常。
2.連接目標(biāo)超時(shí)connectionTimeout
指的是連接目標(biāo)url的連接超時(shí)時(shí)間,即客服端發(fā)送請(qǐng)求到與目標(biāo)url建立起連接的最大時(shí)間。如果在該時(shí)間范圍內(nèi)還沒(méi)有建立起連接,則就
拋出connectionTimeOut異常。如測(cè)試的時(shí)候,將url改為一個(gè)不存在的url:http://test.com ,超時(shí)時(shí)間3000ms過(guò)后,系統(tǒng)報(bào)出異常:
org.apache.commons.httpclient.ConnectTimeoutException:The
host did not accept the connection within timeout of 3000 ms
3.等待響應(yīng)超時(shí)(讀取數(shù)據(jù)超時(shí))socketTimeout
連接上一個(gè)url后,獲取response的返回等待時(shí)間 ,即在與目標(biāo)url建立連接后,等待放回response的最大時(shí)間,在規(guī)定時(shí)間內(nèi)沒(méi)有返回響應(yīng)的話(huà)就拋出SocketTimeout。
測(cè)試的時(shí)候的連接url為我本地開(kāi)啟的一個(gè)url,http://localhost:8080/firstTest.htm?method=test,在我這個(gè)測(cè)試url里,當(dāng)訪(fǎng)問(wèn)到這個(gè)鏈接時(shí),線(xiàn)程sleep一段時(shí)間,來(lái)模擬返回response超時(shí)。
三個(gè)超時(shí)時(shí)間詳解:
1.從連接池中獲取可用連接超時(shí)
HttpClient中的要用連接時(shí)嘗試從連接池中獲取,若是在等待了一定的時(shí)間后還沒(méi)有獲取到可用連接(比如連接池中沒(méi)有空閑連接了)
則會(huì)拋出獲取連接超時(shí)異常。
2.連接目標(biāo)超時(shí)connectionTimeout
指的是連接目標(biāo)url的連接超時(shí)時(shí)間,即客服端發(fā)送請(qǐng)求到與目標(biāo)url建立起連接的最大時(shí)間。如果在該時(shí)間范圍內(nèi)還沒(méi)有建立起連接,則就
拋出connectionTimeOut異常。如測(cè)試的時(shí)候,將url改為一個(gè)不存在的url:http://test.com ,超時(shí)時(shí)間3000ms過(guò)后,系統(tǒng)報(bào)出異常:
org.apache.commons.httpclient.ConnectTimeoutException:The
host did not accept the connection within timeout of 3000 ms
3.等待響應(yīng)超時(shí)(讀取數(shù)據(jù)超時(shí))socketTimeout
連接上一個(gè)url后,獲取response的返回等待時(shí)間 ,即在與目標(biāo)url建立連接后,等待放回response的最大時(shí)間,在規(guī)定時(shí)間內(nèi)沒(méi)有返回響應(yīng)的話(huà)就拋出SocketTimeout。
參考資料
http://blog.csdn.net/u011191463/article/details/78664896
總結(jié)
以上是生活随笔為你收集整理的HttpClient库设置超时的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。