Bash: istruzione If / Else in una riga


204

Sto cercando di verificare se un processo (supponiamo che sia chiamato some_process) è in esecuzione su un server. Se lo è, allora echo 1, altrimenti echo 0.

Questo è il comando che sto usando ma funziona solo parzialmente (maggiori informazioni di seguito). Nota che devo scrivere lo script in una riga.

ps aux | grep some_proces[s] > /tmp/test.txt && if [ $? -eq 0 ]; then echo 1; else echo 0; fi

Nota: Il [s]in some_proces[s]è quello di evitare grepdi tornare in sé.

Se some_processè in esecuzione, "1"viene ripetuto, il che va bene. Tuttavia, se some_processnon è in esecuzione, nulla viene ripetuto.


4
È possibile utilizzare ps -Ccmdper trovare processi il cui nome del comando è "cmd", che può eliminare completamente il file grep. psimposterà il codice di uscita su un valore diverso da zero se non riesce a trovare un processo corrispondente.
rici,

Risposte:


273

Non è necessario controllare esplicitamente $?. Basta fare:

ps aux | grep some_proces[s] > /tmp/test.txt && echo 1 || echo 0 

Si noti che ciò si basa sul fatto che l'eco non fallisca, il che non è certo garantito. Un modo più affidabile per scrivere questo è:

if ps aux | grep some_proces[s] > /tmp/test.txt; then echo 1; else echo 0; fi

9
In caso echo 1contrario, echo 0verrà eseguito. In questo caso, l'eco 1 non fallirà mai, ma nota che A&& B || C non è if-then-else. C può essere eseguito quando A è vero. (Da shellcheck ).
Schemacs,

@schemacs fa un punto molto valido: l'editing per fornire un'alternativa molto migliore.
William Pursell,

2
È necessario reindirizzare l'output del comando ps su un file? Non funzionerebbe? if ps aux | grep some_proces[s]; then echo 1; else echo 0; fi. A livello locale sembra funzionare per me. È perché OP ha avuto il reindirizzamento nel comando che ha provato?

1
Non è assolutamente necessario reindirizzare l'output. Ho semplicemente preferito la posizione originale, dato che suppongo che l'output sia stato salvato per un motivo. Spesso questo genere di cose viene semplicemente soppresso (con grep -qo reindirizzato a / dev / null).
William Pursell,

Vorrei usare pgrep.
pawciobiel,

67

&&significa "e se ha successo"; posizionando la tua ifdichiarazione sul lato destro, ti assicuri che verrà eseguita solo se greprestituisce 0. Per risolverlo, utilizzare ;invece:

ps aux | grep some_proces[s] > /tmp/test.txt ; if [ $? -eq 0 ]; then echo 1; else echo 0; fi

(o semplicemente usa un'interruzione di riga).


6
+1 Questa è una risposta molto migliore, poiché in realtà risponde alla domanda invece di fornire semplicemente un'alternativa.
William Pursell,

41

Utilizzare grep -vcignorare grepin psuscita e contare le linee contemporaneamente.

if [[ $(ps aux | grep process | grep -vc grep)  > 0 ]] ; then echo 1; else echo 0 ; fi

15

È possibile utilizzare appieno gli operatori &&e in ||questo modo:

ps aux | grep some_proces[s] > /tmp/test.txt && echo 1 || echo 0

Per escludere grep stesso, potresti anche fare qualcosa del tipo:

ps aux | grep some_proces | grep -vw grep > /tmp/test.txt && echo 1 || echo 0

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.