从Java代码检查服务器是否在线

我想检查服务器应用程序是否可用。 服务器启动后,我想停止检查,直到服务器更改状态。 如何使用我的代码:

private static final String SERVER_ADDRESS = "192.144.10.10"; private static final int TCP_SERVER_PORT = 8890; private static boolean connected = false; static Socket s; public static void main(String[] args) { Timer timer = new Timer(); timer.schedule(task, 01, 5001); } static TimerTask task = new TimerTask() { @Override public void run() { // TODO Auto-generated method stub if (connected == false) { System.out.println(hostAvailabilityCheck()); } } }; public static boolean hostAvailabilityCheck() { boolean available = true; try { if (connected == false) { (s = new Socket(SERVER_ADDRESS, TCP_SERVER_PORT)).close(); } } catch (UnknownHostException e) { // unknown host available = false; s = null; } catch (IOException e) { // io exception, service probably not running available = false; s = null; } catch (NullPointerException e) { available = false; s=null; } return available; } 

有没有更好的方法来解决这个问题?

check方法可以重写如下(Java 7及更高版本):

 public static boolean hostAvailabilityCheck() { try (Socket s = new Socket(SERVER_ADDRESS, TCP_SERVER_PORT)) { return true; } catch (IOException ex) { /* ignore */ } return false; } 

除了简化exception处理之外,这还消除了令人讨厌的Socket泄漏。 (如果您担心执行此检查所花费的时间,请在尝试连接之前设置连接超时:请参阅设置套接字操作的超时 )

但这种方法的问题有很多:

  • 它只测试某些东西正在监听连接。 如果您的服务在代理服务器后面……或者由inetd服务之类的东西管理……那么接受的连接并不意味着您的服务实际上正在运行。

  • 这将导致您的服务“看到”关闭而不发送请求的连接。 因此,您最好对您的服务进行编码,以“优雅地”处理此问题。

  • 重复这样做会增加网络和服务器负载。

  • 如果您因为不希望测试“冻结”而设置短暂超时,那么您可能会将其设置得太短并且判断主机在没有时关闭。


服务器启动后,我想停止检查,直到服务器更改状态

这几乎是不可能的。 原因是如果不检查,您将无法判断服务器是否已“更改状态”。 或者至少,如果没有实现精心设置的状态通知服务,服务器会调用客户端告诉它正在更改状态,您将无法执行此操作。 (如果“更改状态”包括“死亡”或“丢失网络连接”,那么您将无法使通知可靠…如果有的话。)

首先检查服务器是否正在运行,服务器是否接受连接。

  public static boolean hostAvailabilityCheck() { s = new Socket(SERVER_ADDRESS, TCP_SERVER_PORT); boolean available = true; try { if (s.isConnected()) { s.close(); } } catch (UnknownHostException e) { // unknown host available = false; s = null; } catch (IOException e) { // io exception, service probably not running available = false; s = null; } catch (NullPointerException e) { available = false; s=null; } return available; } 
 public static boolean hostAvailabilityCheck() { try (Socket s = new Socket(SERVER_ADDRESS, TCP_SERVER_PORT)) { return true; } catch (IOException ex) { /* ignore */ } return false; } 

工作,但问题是当你通过WI-FI打开手机时,它会“戛然而止”并且没有动作。 为了思考…… =)

下一个代码将通过WI-FI工作…如果你增加连接时间 –

 public static boolean isOnline() { boolean b = true; try{ InetSocketAddress sa = new InetSocketAddress("SERVER_IP_ADDRESS", PORT); Socket ss = new Socket(); ss.connect(sa, 1); --> change from 1 to 500 (for example) ss.close(); }catch(Exception e) { b = false; } return b; } 

我在ServerUtil中使用了这种方法。

  public static boolean isOnline() { boolean b = true; try{ InetSocketAddress sa = new InetSocketAddress("SERVER_IP_ADDRESS", PORT); Socket ss = new Socket(); ss.connect(sa, 1); ss.close(); }catch(Exception e) { b = false; } return b; }