如何在端口扫描仪Java实现中检测服务器状态
-
03-10-2019 - |
题
我正在Java编写端口扫描仪,我希望能够区分以下四种用例:
- 端口开放
- 端口开放,读取服务器横幅
- 端口关闭
- 服务器不存在
我有以下代码:
InetAddress address = InetAddress.getByName("google.com");
int[] ports = new int[]{21, 22, 23, 80, 443};
for (int i = 0; i < ports.length; i++) {
int port = ports[i];
Socket socket = null;
try {
socket = new Socket(address, port);
socket.setSoTimeout(500);
System.out.println("port " + port + " open");
BufferedReader reader = new BufferedReader(
new InputStreamReader(socket.getInputStream()));
String line = reader.readLine();
if (line != null) {
System.out.println(line);
}
socket.close();
} catch (SocketTimeoutException ex) {
// port was open but nothing was read from input stream
ex.printStackTrace();
} catch (ConnectException ex) {
// port is closed
ex.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (socket != null && !socket.isClosed()) {
try {
socket.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
问题在于,当关闭端口并且无法达到服务器时,我都会获得连接exception,但除了不同的例外消息:
java.net.connectException: 连接超时:连接
当连接从未建立时
java.net.connectException: 连接被拒绝:连接
港口关闭时
因此,我无法在不挖掘实际异常消息的情况下将两个用例之间的区别。
当我尝试使用其他方法来创建插座时,也会发生同样的事情。如果我使用:
socket = new Socket();
socket.setSoTimeout(500);
socket.connect(new InetSocketAddress(address, port), 1000);
我有同样的问题,但是使用sockettimeoutexception。我得到一个
java.net.sockettimeoutexception: 读取超时
如果港口开放,但没有旗帜可以阅读和
java.net.sockettimeoutexception: 连接时间
如果服务器不使用 或者 端口关闭。
有任何想法吗?提前致谢!
解决方案
除了解析异常消息之外,我认为您没有任何选择。有什么原因您不想这样做吗?
其他提示
ConnectException 只有一个空的构造函数和一个错误的构造函数。 API中没有ConnectException的子类。因此,恐怕Java没有适当的方法来访问原因。解析异常消息似乎是唯一的方法,尽管它确实对翻译很混乱。
不隶属于 StackOverflow