2011-10-31 44 views
10

我有一个简单的服务器客户端应用程序。一切正常,但在某个阶段,从服务器获得响应需要5分钟以上(这是正常的,它需要这样)。问题是,如果超过5分钟,我会收到这个例外:java.net.SocketTimeoutException: Read timed outJava,增加套接字超时

所以我想知道是否有一些默认套接字超时在Windows上或我可以设置的Java虚拟机?我无法更改客户端代码,所以setSoTimeout()不适合我。

使用Windows XP ..

编辑:由于我现在明白的是,插座连接没有在客户端打开。它从服务器传递。所以我反编译的服务器jar文件。但仍然无法找到关于超时的任何事情。

+0

检查是否使用系统属性配置了超时。 – JimmyB

+0

@HannoBinder,你能解释一下系统属性是什么意思吗? – hs2d

+0

我的意思是像[sun.net.client.defaultReadTimeout](http://download.oracle.com/javase/1.4.2/docs/guide/net/properties.html)或任何可能适用于您客户的方式的连接。 – JimmyB

回答

10

默认套接字超时值为0,表示永不超时。如果5分钟后实际超时,则意味着它已在代码中设置。如果源不可用,并且没有配置,则可以尝试反编译该类,然后查找setSoTimeout调用。

由于注释以及搜索未找到任何setSoTimeout()调用的事实,您可以采取不同的方法。只要让它超时,并写一个小脚本,以防万一它会重试呼叫。如果你可以从命令行调用你的客户端,你可以解析输出,如果它发生在stderr上。

+0

我反编译并寻找'setSoTimeout'调用,但没有发现任何东西。它必须设置在别的地方呢? – hs2d

8

保持未使用的TCP连接长时间打开并且没有任何流量并不是那么简单。许多防火墙/路由器在超时后关闭未使用的端口。

一个选项可能是实现简单的keepalive协议来不时发送虚拟数据包,但如果你不能触摸客户端代码,这可能不是一个选项。

编辑:我不知道有什么方法来覆盖setSoTimeout()在客户端代码中设置。

+0

非常好的主意与保持活着的数据包! – benez

+0

@ benez我不同意。如果路由器将连接看作是一种宝贵的资源,并将其连接起来,那么您就不会有任何业务欺骗它来保持连接。无论如何,你仍然必须处理连接损失。添加Keepalive乒乓确实是脖子上毫无意义的痛苦。 – EJP

+0

@EJP我还没有看到适当的实现来处理连接损失。有些情况下您正在等待实时更新,并且您需要不断连接两方以保持其数据同步。连接损失不能简单地通过简单的重新连接来处理。你会错过一个重要的信息或迟到。例如股市总是发出心跳,IRC协议要求你用乒乓回答ping。是的,你必须处理连接损失,但你可能想在某些程序中避免它们。 – benez

0

回答说,0是默认超时不完全正确。例如,由于Axis2客户端具有默认的60秒超时时间,因此它将取决于您使用何种类型的实现进行呼叫。

你能提供更多细节吗?对不起,写在答案部分,但我没有足够的声誉做评论:)

+0

看看这里的代码,我只能看到'java.io.InputStream'。所以连接必须从服务器到客户端完成? – hs2d

+0

好吧,是的,对于Java而言,默认值是无限的,但是一个库可能会改变它。也许是一个提示,hs2d,你有任何jar包括?或者,也许你可以采取不同的方法,只要让它超时并在失败时重试。 – stivlo

0

你需要保持连接活着吗?为什么不重新考虑它使它更加异步。该架构根本不能扩展。有一次,所有可用的线程都可能等待服务器的长时间响应。

+0

如果他想从中读取连接,他需要保持连接正常。无法做出所有这些的头部或尾部。 – EJP