HttpURLConnection中设置网络超时

/ Java / 没有评论 / 2031浏览

HttpURLConnection中设置网络超时

Java中可以使用HttpURLConnection来请求WEB资源。HttpURLConnection对象不能直接构造,需要通过URL.openConnection()来获得HttpURLConnection对象,示例代码如下:

String urlStr= [www.jaddy.org](http://www.jaddy.org/);
URL url = new URL(urlStr);
HttpURLConnection conn = (HttpURLConnection)url.openConnection();

HttpURLConnection是基于HTTP协议的,其底层通过socket通信实现。如果不设置超时(timeout),在网络异常的情况下,可能会导致程序僵死而不继续往下执行。可以通过以下两个语句来设置相应的超时:

System.setProperty("sun.net.client.defaultConnectTimeout", 超时毫秒数字符串);
System.setProperty("sun.net.client.defaultReadTimeout", 超时毫秒数字符串);

其中:

例如:

System.setProperty("sun.net.client.defaultConnectTimeout", "30000");
System.setProperty("sun.net.client.defaultReadTimeout", "30000");

JDK 1.5以前的版本,只能通过设置这两个系统属性来控制网络超时。在1.5中,还可以使用HttpURLConnection的父类URLConnection的以下两个方法:

例如:

HttpURLConnection urlCon = (HttpURLConnection)url.openConnection();
urlCon.setConnectTimeout(30000);
urlCon.setReadTimeout(30000);

备注: 我在项目中碰到这个问题比较隐蔽,开始我以为是线程死锁造成我的线程无法执行下去,后来我用 Java visualVM工具显示的线程DUMP堆信息:

"Tue Jun 17 09:41:40 CST 2014172.16.11.107" daemon prio=6 tid=0x0db77c00 nid=0x1470 runnable [0x0f43f000]
   java.lang.Thread.State: RUNNABLE
at java.net.SocketInputStream.socketRead0(Native Method)
at java.net.SocketInputStream.read(SocketInputStream.java:129)
at java.io.BufferedInputStream.fill(BufferedInputStream.java:218)
at java.io.BufferedInputStream.read1(BufferedInputStream.java:258)
at java.io.BufferedInputStream.read(BufferedInputStream.java:317)
\- locked <0x06735a50> (a java.io.BufferedInputStream)
at sun.net.www.http.HttpClient.parseHTTPHeader(HttpClient.java:687)
at sun.net.www.http.HttpClient.parseHTTP(HttpClient.java:632)
at sun.net.www.protocol.http.HttpURLConnection.getInputStream(HttpURLConnection.java:1064)
\- locked <0x06735a88> (a sun.net.www.protocol.http.HttpURLConnection)
at sun.net.www.protocol.http.HttpURLConnection.getHeaderFields(HttpURLConnection.java:2187)
at com.zzst.application.meeting.mcu.operate.rmx2000.RMX2000Sender.sendPost(RMX2000Sender.java:86)
at com.zzst.application.meeting.mcu.operate.rmx2000.RMX2000Sender.sendPost(RMX2000Sender.java:35)
at com.zzst.application.meeting.mcu.operate.rmx2000.ZZMCU2000ContactHandler.contact(ZZMCU2000ContactHandler.java:124)
at com.zzst.application.meeting.mcu.operate.rmx2000.ZZMCU2000ContactHandler.run(ZZMCU2000ContactHandler.java:65)
at java.lang.Thread.run(Thread.java:619)
   Locked ownable synchronizers:
\- None

从这个堆信息可以看出,停在“HttpURLConnection.getHeaderFields”语句处。现在我在我的程序里设置了连接主机超时和从主句中获取数据超时两个参数,看看接下来系统运行效果如何。