Isso é bom de alguma forma (fará o que eu quero?)
Você pode fazer isso. Outra maneira viável é usar java.net.Socket
.
public static boolean pingHost(String host, int port, int timeout) {
try (Socket socket = new Socket()) {
socket.connect(new InetSocketAddress(host, port), timeout);
return true;
} catch (IOException e) {
return false; // Either timeout or unreachable or failed DNS lookup.
}
}
Há também o InetAddress#isReachable()
:
boolean reachable = InetAddress.getByName(hostname).isReachable();
No entanto, isso não testa explicitamente a porta 80. Você corre o risco de obter falsos negativos devido a um firewall bloqueando outras portas.
Preciso fechar a conexão de alguma forma?
Não, você não precisa explicitamente. É tratado e agrupado sob os capuzes.
Suponho que seja uma solicitação GET. Existe uma maneira de enviar HEAD?
Você pode converter o obtido URLConnection
em HttpURLConnection
e, em seguida, usar setRequestMethod()
para definir o método de solicitação. No entanto, é necessário levar em consideração que alguns aplicativos da Web pobres ou servidores domésticos podem retornar um erro HTTP 405 para um HEAD (ou seja, não disponível, não implementado, não permitido) enquanto um GET funciona perfeitamente. O uso de GET é mais confiável caso você pretenda verificar links / recursos, não domínios / hosts.
Testar a disponibilidade do servidor não é suficiente no meu caso, preciso testar o URL (o aplicativo da web pode não estar implantado)
De fato, conectar um host apenas informa se o host está disponível, não se o conteúdo está disponível. Pode acontecer que um servidor da Web tenha iniciado sem problemas, mas o aplicativo da Web falhou ao implantar durante o início do servidor. No entanto, isso geralmente não causa a inatividade do servidor inteiro. Você pode determinar isso verificando se o código de resposta HTTP é 200.
HttpURLConnection connection = (HttpURLConnection) new URL(url).openConnection();
connection.setRequestMethod("HEAD");
int responseCode = connection.getResponseCode();
if (responseCode != 200) {
// Not OK.
}
// < 100 is undetermined.
// 1nn is informal (shouldn't happen on a GET/HEAD)
// 2nn is success
// 3nn is redirect
// 4nn is client error
// 5nn is server error
Para obter mais detalhes sobre os códigos de status de resposta, consulte a seção 10 da RFC 2616 . A chamada connect()
não é necessária se você estiver determinando os dados da resposta. Ele se conectará implicitamente.
Para referência futura, veja um exemplo completo do sabor de um método utilitário, também levando em consideração os tempos limite:
/**
* Pings a HTTP URL. This effectively sends a HEAD request and returns <code>true</code> if the response code is in
* the 200-399 range.
* @param url The HTTP URL to be pinged.
* @param timeout The timeout in millis for both the connection timeout and the response read timeout. Note that
* the total timeout is effectively two times the given timeout.
* @return <code>true</code> if the given HTTP URL has returned response code 200-399 on a HEAD request within the
* given timeout, otherwise <code>false</code>.
*/
public static boolean pingURL(String url, int timeout) {
url = url.replaceFirst("^https", "http"); // Otherwise an exception may be thrown on invalid SSL certificates.
try {
HttpURLConnection connection = (HttpURLConnection) new URL(url).openConnection();
connection.setConnectTimeout(timeout);
connection.setReadTimeout(timeout);
connection.setRequestMethod("HEAD");
int responseCode = connection.getResponseCode();
return (200 <= responseCode && responseCode <= 399);
} catch (IOException exception) {
return false;
}
}