Bash: If / Else-Anweisung in einer Zeile

204

Ich versuche zu überprüfen, ob ein Prozess (vorausgesetzt, er wird aufgerufen some_process) auf einem Server ausgeführt wird. Wenn ja, dann Echo 1, andernfalls Echo 0.

Dies ist der Befehl, den ich verwende, der jedoch nur teilweise funktioniert (weitere Informationen unten). Beachten Sie, dass ich das Skript in einer Zeile schreiben muss.

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

Hinweis: Das [s]In some_proces[s]soll verhindern, dass grepes sich selbst zurückgibt.

Wenn some_processes läuft, "1"wird es wiedergegeben, was in Ordnung ist. Wenn some_processes jedoch nicht ausgeführt wird, wird nichts wiedergegeben.

Arthur Rimbun
quelle
4
Sie können ps -Ccmddamit Prozesse suchen, deren Befehlsname "cmd" ist, wodurch das vollständig beseitigt werden kann grep. pssetzt den Exit-Code auf einen Wert ungleich Null, wenn kein passender Prozess gefunden wird.
Rici

Antworten:

272

Es besteht keine Notwendigkeit, dies explizit zu überprüfen $?. Mach einfach:

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

Beachten Sie, dass dies darauf beruht, dass das Echo nicht ausfällt, was sicherlich nicht garantiert ist. Eine zuverlässigere Möglichkeit, dies zu schreiben, ist:

if ps aux | grep some_proces[s] > /tmp/test.txt; then echo 1; else echo 0; fi
William Pursell
quelle
9
Wenn echo 1fehlschlagen, echo 0wird ausgeführt. In diesem Fall wird Echo 1 niemals fehlschlagen. Beachten Sie jedoch, dass A && B || C ist nicht wenn-dann-sonst. C kann ausgeführt werden, wenn A wahr ist (vom Shellcheck ).
Schema
@schemacs macht einen sehr gültigen Punkt: Bearbeiten, um eine viel bessere Alternative zu bieten.
William Pursell
2
Muss die Ausgabe des Befehls ps in eine Datei umgeleitet werden? Würde das nicht funktionieren? if ps aux | grep some_proces[s]; then echo 1; else echo 0; fi. Vor Ort scheint es für mich zu funktionieren. Liegt es daran, dass OP die Umleitung in dem Befehl hatte, den er versucht hat?
1
Es ist absolut nicht erforderlich, die Ausgabe umzuleiten. Ich mache nur die ursprüngliche Position nach, da ich davon ausgehe, dass die Ausgabe aus einem bestimmten Grund gespeichert wird. Oft wird so etwas nur unterdrückt (mit grep -qoder nach / dev / null umgeleitet).
William Pursell
Ich würde verwenden pgrep.
Pawciobiel
67

&&bedeutet "und wenn erfolgreich"; indem Sie Ihre Platzierung ifErklärung auf der rechten Seite davon, stellen Sie sicher , dass es nur dann , wenn läuft grepzurückkehrt 0. Verwenden Sie, um das Problem zu beheben; stattdessen Problem :

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

(oder verwenden Sie einfach einen Zeilenumbruch).

Ruakh
quelle
6
+1 Dies ist eine viel bessere Antwort, da sie die Frage tatsächlich beantwortet, anstatt lediglich eine Alternative bereitzustellen.
William Pursell
41

Verwenden Sie grep -vcdiese Option, grepum die psAusgabe zu ignorieren und die Zeilen gleichzeitig zu zählen.

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

Sie können die Operatoren &&und ||wie folgt vollständig nutzen :

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

Um grep selbst auszuschließen, können Sie auch Folgendes tun:

ps aux | grep some_proces | grep -vw grep > /tmp/test.txt && echo 1 || echo 0
Costi Ciudatu
quelle
2
pgrep -q some_process && echo 1 || echo 0

mehr Oneliner hier

Einmal
quelle