2017-07-26 30 views
0

我有Java代码在特定端口上设置服务器,某些代码在使用此服务器的python中运行,然后端口关闭。我已经设置好了,所以在每次python运行后,java循环并重复这个过程(建立一个新的服务器,服务,然后关闭)。将连续的JVM绑定调用限制到同一端口

我注意到,当python调用很短(约为< 10秒)时,下次Java尝试设置此端口时,它将失败。在Java中连续设置相同端口之间需要等待多长时间才有规则?

+2

这可能取决于操作系统。 – Robert

+2

通常,您将保持服务器套接字处于打开状态,并接受并关闭传入的连接。然后等待同一服务器套接字上的下一个传入连接。 – Henry

回答

1

端口可以挑剔这种类型的东西。他们不打算一直打开和关闭。你应该把socket公开,公正的处理中的每个连接,就像这样:

ServerSocket listener = new ServerSocket(9090); 
    try { 
     while (true) { 
      Socket socket = listener.accept(); 
      try { 
       PrintWriter out = 
        new PrintWriter(socket.getOutputStream(), true); 
       out.println(new Date().toString()); 
      } finally { 
       socket.close(); 
      } 
     } 
    } 
    finally { 
     listener.close(); 
    } 

(来源:http://cs.lmu.edu/~ray/notes/javanetexamples/

+1

不,您应该为每个传入连接启动一个单独的线程。如果你不这样做,那么当你的套接字处理器正在运行时,你的服务器不能做任何事情。 –

+2

@JimGarrison OP一次只暗示一个客户。如果没有必要,我认为没有理由引入复杂性。 –

+0

@DanielCentore它*是* nessary。对接受的套接字的任何I/O都可以阻塞,如果它在接受线程中完成,则阻塞下一个连接。 – EJP

1

在一般情况下,最好是维持一个长期运行的ServerSocket,供应多个请求,正如其他人已经回答和评论的那样。但是,我发现有时需要快速连续停止和启动服务器。一个示例是集成测试套件,它涉及停止并重新启动不同配置的服务器以重复测试运行。

如果您确实有此需求,那么您可能会对ServerSocket#setReuseAddress(boolean)感兴趣。

启用/禁用SO_REUSEADDR套接字选项。 当TCP连接关闭时,连接关闭后(通常称为TIME_WAIT状态或2MSL等待状态),连接可能会保持超时状态一段时间。对于使用众所周知的套接字地址或端口的应用程序,如果在涉及套接字地址或端口的超时状态中存在连接,则可能无法将套接字绑定到所需的套接字地址。

使用bind(SocketAddress)绑定套接字之前启用SO_REUSEADDR允许套接字被绑定,即使先前的连接处于超时状态。

这最终启用了SO_REUSEADDR套接字选项。有关这些套接字选项的更多详细信息的一个信息来源是Linux socket手册页。

但是,请注意,确切的感知行为在不同的平台上可能会非常大。特别是,请注意MSDN文章Using SO_REUSEADDR and SO_EXCLUSIVEADDRUSE中记录的此设置在Windows上的极端不同且危险的行为。基本上,Windows上的SO_REUSEADDR可以允许任意进程“窃取”已被另一进程使用的套接字,从而导致不确定的行为。

SO_REUSEADDR套接字选项允许套接字强制绑定到另一个套接字使用的端口。第二个套接字调用setsockopt,将optname参数设置为SO_REUSEADDR,将optval参数设置为布尔值TRUE,然后调用与原始套接字相同的端口上的绑定。一旦第二个套接字成功绑定,绑定到该端口的所有套接字的行为就是不确定的。例如,如果同一端口上的所有套接字都提供TCP服务,则通过端口传入的任何TCP连接请求都无法保证被正确的套接字处理 - 这种行为是非确定性的。恶意程序可以使用SO_REUSEADDR强制绑定已用于标准网络协议服务的套接字,以拒绝对这些服务的访问。使用此选项不需要特殊权限。

我建议人们仔细思考,并确保您对此设置有信心,而不是盲目打开它。还有一个现象之前的问题和答案对相关的套接字选项:

Socket options SO_REUSEADDR and SO_REUSEPORT, how do they differ? Do they mean the same across all major operating systems?

+0

很难理解微软为什么不修正他们的SO_REUSEADDR实现来同意其他人的意见,而不是在整个地方散布关于它的警告。关于客户端和服务器绑定到同一端口的以下段落甚至没有意义。 – EJP

+0

@EJP,很好的问题!也许他们保持全能的向后兼容行为?我不知道。 –

+0

我怀疑他们可能有一些依赖于这个bug的内部“特性”。 – EJP

相关问题