在流上执行GET时,HTTPClient永远不会离开socketRead() - 解决方法?

时间:2013-11-12 01:11:51

标签: java apache-httpclient-4.x

我正在使用Apache HttpClient(来自Apache HTTP Components 4.3),以便针对ShoutCast流执行GET:

CloseableHttpClient client = HttpClients.createDefault();
HttpGet request = new HttpGet("http://relay3.181.fm:8062/");
CloseableHttpResponse response = client.execute(request);

对client.execute()的调用永远不会返回,并且根据调试器,它是对java.net.SocketInputStream#socketRead0()的嵌套调用,这是调用堆栈中的最后一个节点。从分析代码中,我唯一的结论(基于逐渐增加的char []分配数量)是它只是“锁定”到流并继续无限期地从套接字中拉出字节。

我希望客户端能够正常工作并给我一个HTTPResponse,我可以使用它来从流中提取我想要的东西。事实上,我已经能够与其他ShoutCast流一起使用,但不是这个。

有什么方法可以解决这个问题吗?我可以告诉客户端在一定数量的字节后中断吗?

1 个答案:

答案 0 :(得分:2)

该网站非常特别。如果您未指定受支持的User-Agent(如Mozilla),则服务器会保留流式字节。我不知道这些字节是什么意思,音频也许。

如果您打印出收到的字节,您将看到

ICY 200 OK
icy-notice1:<BR>This stream requires <a href="http://www.winamp.com/">Winamp</a><BR>
icy-notice2:SHOUTcast Distributed Network Audio Server/Linux v1.9.8<BR>
icy-name:181.FM - The Beatles Channel
icy-genre:Oldies
icy-url:http://www.181.fm
content-type:audio/mpeg
icy-pub:1
icy-br:128

表示响应不是有效的HTTP响应。这是ICY协议的ICY回复。

现在,您使用的默认HttpClient使用的是DefaultHttpResponseParser

  

可以跳过格式错误的宽松HTTP响应解析器实现   数据,直到遇到有效的HTTP响应消息头。

换句话说,它会一直读取服务器发送的字节,直到找到一个永远不会发生的有效HTTP响应头,从而无限次读取。

我认为您无法通过Http Components库完成您想要的任务。要么在Java中查找ICY客户端实现,要么自己创建。