Come creare un loop in bash che aspetta che un server web risponda?


105

Come creare un loop in bash che aspetta che un server web risponda?

Dovrebbe stampare un "." ogni 10 secondi circa e attendere che il server inizi a rispondere.

Aggiornamento, questo codice verifica se ottengo una buona risposta dal server.

if curl --output / dev / null --silent --head --fail "$ url"; poi
  echo "URL esistente: $ url"
altro
  echo "L'URL non esiste: $ url"
fi

Puoi essere più specifico su come stai aspettando che il server risponda?
chepner

Considererò che il server non è pronto, purché non risponda o risponda con qualcosa di diverso da una risposta 200.
sorin

Risposte:


173

Combinando la domanda con la risposta di Chepner, questo ha funzionato per me:

until $(curl --output /dev/null --silent --head --fail http://myhost:myport); do
    printf '.'
    sleep 5
done

10
L'uso di backtick `` è obsoleto . Usa $( )invece.
Serge Stroobandt

6
Sarebbe una grande estensione per consentire un tempo massimo di attesa prima di arrendersi
tkruse

Perché hai bisogno di un --head?
lexicore

3
@lexicore Dato che il corpo non è interessante per questo comando, richiediamo solo la testata (sebbene tu possa includere la logica per controllare più cose sullo stato del server). Tralasciando --headnon cambierebbe nulla, ma potresti farlo se vuoi esercitare un po 'di logica sui contenuti della risposta (come uno status.html).
Thomas Ferris Nicolaisen

1
Ho avuto un caso specifico in cui l'utilizzo è --headsempre tornato 405. Ho dovuto rimuoverlo per farlo funzionare
Ron Harlev

38

Volevo limitare il numero massimo di tentativi. Sulla base della risposta accettata di Thomas, ho fatto questo:

attempt_counter=0
max_attempts=5

until $(curl --output /dev/null --silent --head --fail http://myhost:myport); do
    if [ ${attempt_counter} -eq ${max_attempts} ];then
      echo "Max attempts reached"
      exit 1
    fi

    printf '.'
    attempt_counter=$(($attempt_counter+1))
    sleep 5
done

Suggerisco di aggiungere --max-time 5se per qualche motivo ha richiesto il timeout del collegamento
Enigo

16

httping è utile per questo. semplice, pulito, silenzioso.

while ! httping -qc1 http://myhost:myport ; do sleep 1 ; done

mentre / until ecc è una pref personale.


2
Ripensandoci, per sempre è un tempo lungo ... for i in seq 60; do httping -qc1 http://myhost:myport && echo && break sleep 5 echo -n ${i}.. done
Bruce Edge

2

L'uso di backtick ` `è obsoleto . Usa $( )invece:

until $(curl --output /dev/null --silent --head --fail http://myhost:myport); do
  printf '.'
  sleep 5
done

0

Interessante puzzle. Se non hai accesso o API asincrona con il tuo client, puoi provare a greppare i tuoi socket tcp in questo modo:

until grep '***IPV4 ADDRESS OF SERVER IN REVERSE HEX***' /proc/net/tcp
do
  printf '.'
  sleep 1
done

Ma questa è un'attesa impegnativa con intervalli di 1 secondo. Probabilmente vuoi una risoluzione maggiore di quella. Anche questo è globale. Se viene stabilita un'altra connessione a quel server, i risultati non sono validi.


-1

se hai bisogno di controllare se il server è disponibile, la causa è il riavvio o qualcos'altro, potresti provare a fare un wget al server e analizzare la risposta o l'errore, se ottieni un 200 o anche un 404 il server è attivo, tu potresti cambiare il timeout di wget con --timeout = seconds, puoi impostare il timeout a 10 secondi e fare un ciclo fino a quando il grep sulla risposta non ha un risultato.

non so se questo è quello che stai cercando o se hai davvero bisogno del codice bash.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.