HttpClient使用方法

HttpClient作为访问Http服务的客户端访问程序已经被广泛使用,对于HttpClient的使用方法也有很多blog进行介绍,本文简明扼要的介绍HttpClient的两种使用方式——简单连接管理的HttpClientBasicClientConnectionManager)和池化的HttpClientPoolingClientConnectionManager)。

HttpClient4.2开始抛弃了先前的SingleClientConnManagerThreadSafeConnManger,取而代之的是BasicClientConnectionManagerPoolingClientConnectionManager

BasicClientConnectionManager内部只维护一个活动的connection,尽管这个类是线程安全的,但是最好在一个单独的线程中重复使用它。如果在同一个BasicClientConnectionManager对象中,多次执行http请求,后继请求与先前请求是同一个route,那么BasicClientConnectionManager会使用同一个连接完成后续请求,否则,BasicClientConnectionManager会将先前的connection关闭,然后为后续请求创建一个新的连接。换句话说,BasicClientConnectionManager会尽力复用先前的连接(注意:创建连接和销毁连接都是不小的开销),因此,如果对同一个service有多个连续请求,应该尽量使用同一个BasicClientConnectionManager完成。

PoolingClientConnectionManager可以在多线程中使用,连接按照route被缓存(pooled),当后续的请求route已经在pool中存在,就会使用pool中先前使用的connection获取请求结果。PoolingClientConnectionManager对每个router维护的connection数目有上限要求,默认情况下,每个router最多维护两个并发线程的connection连接,整个pool最多容纳20个并发的connections。当然可以通过设置来修改这些限制。

下面给出两个例子:

Demo 1BasicClientConnectionManager

    public static void basicClientTest() throws ClientProtocolException, IOException{

       HttpClient httpClient = new DefaultHttpClient();

       HttpGet httpGet = new HttpGet("http://m.weather.com.cn/data/101010100.html");

       HttpResponse response = httpClient.execute(httpGet);

       String result = EntityUtils.toString(response.getEntity(), Charset.forName("utf-8"));

       System.out.println(result);

       httpClient.getConnectionManager().shutdown();

    }

Demo1中,使用最简单的方式创建的httpclient内部使用的是BasicClientConnectionManager管理连接,并且使用HttpClient提供的EntityUtils将消息体转换成String输出。httpClient对象可以被重复使用,执行多个http请求,当你真正不需要他的时候,记得调用shutdown,关闭并且释放占用的资源。

Demo2PoolingClientConnectionManager

    public static void httpclientPool() throws ClientProtocolException, IOException{

       SchemeRegistry registry = new SchemeRegistry();//创建schema

      

       SSLContext sslContext = null;//https类型的消息访问

       try{

           sslContext = SSLContext.getInstance("SSL");

           sslContext.init(null, null, null);

       }

       catch (Exception e) {

           e.printStackTrace();

       }

       SSLSocketFactory sslFactory =newSSLSocketFactory(sslContext,SSLSocketFactory.STRICT_HOSTNAME_VERIFIER);

       registry.register(new Scheme("http", 80, PlainSocketFactory.getSocketFactory()));//http 80 端口

       registry.register(new Scheme("https", 443, sslFactory));//https 443端口

      

       PoolingClientConnectionManager cm = newPoolingClientConnectionManager(registry);//创建connectionManager

      

       cm.setDefaultMaxPerRoute(20);//对每个指定连接的服务器(指定的ip)可以创建并发20 socket进行访问

       cm.setMaxTotal(200);//创建socket的上线是200

       HttpHost localhost = new HttpHost("locahost", 80);

       cm.setMaxPerRoute(new HttpRoute(localhost), 80);//对本机80端口的socket连接上限是80

      

       HttpClient httpClient = new DefaultHttpClient(cm);//使用连接池创建连接

       HttpParams params = httpClient.getParams();

       HttpConnectionParams.setSoTimeout(params, 60*1000);//设定连接等待时间

       HttpConnectionParams.setConnectionTimeout(params, 60*1000);//设定超时时间

 

       try{

           HttpGet httpGet = new HttpGet("http://m.weather.com.cn/data/101010100.html");

           HttpResponse response = httpClient.execute(httpGet);

           String result = EntityUtils.toString(response.getEntity(), Charset.forName("utf-8"));

           System.out.println(result);

       }finally{

           httpClient.getConnectionManager().shutdown();//用完了释放连接

       }

      

    }

PoolingClientConnectionManager的创建过程要比BasicClientConnectionManager复杂的多,当然,我们为了举例子,将PoolingClientConnectionManager可能涉及到的多个方面属性都列出来,可以根据需要设置或者使用默认的连接属性。首先我们创建了SchemeRegistry,之后注册了两种http访问方式httphttps,创建PoolingClientConnectionManager,指定每个router最多保持20个活动的connection,这个pool最多保持200个活动的connection,对本地的访问可以保持80个活动的connection。最后创建httpClient,设置SO_TIMEOUTCONNECTION_TIMEOUT,执行请求。在httpClient不再使用时,关闭connectionManager

Demo2 只是个例子,说明应当如何创建一个带有缓冲池的HttpClient,在实际应用中,可以对多个访问共用一个池化的HttpClient,即提高了性能(重用connectionconnectiondisconnect是非常耗时的,要选路由,三次握手等),也方便了管理,有利于代码的维护。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值