So speichern Sie stdout in einer Datei, stderr in einer Datei, stdout+stderr in einer Datei und erhalten stdout + stderr wie üblich für ein Shell-Skript zum Terminal

So speichern Sie stdout in einer Datei, stderr in einer Datei, stdout+stderr in einer Datei und erhalten stdout + stderr wie üblich für ein Shell-Skript zum Terminal

Wie kann ich stdout in einer Datei, stderr in einer anderen Datei, stdout+stderr in einer dritten Datei speichern und außerdem stdout + stderr wie üblich für ein Shell-Skript zum Terminal bringen?

Ich habe das hier woanders gefunden:

exec > >(tee std_out) 2> >(tee err_out >&2)
ls # Should got to std_out
fsdfs # Command not found goes to err_out

Das ist wirklich nah dran. Wenn ich bash test.sh 2>&1 | tee outputes ausführe, funktioniert es, aber ich habe keinen Zugriff darauf, wie mein Skript ausgeführt wird. Es ist ein CICD-System. Ich muss in der Lage sein, die „kombinierte Ausgabe“ aus dem Skript heraus mit exec zu erstellen.

Ich erstelle eine CI/CD-Bibliothek und weiß nicht, wofür die Clients die Bibliothek verwenden würden. Deshalb möchte ich jeden Anwendungsfall berücksichtigen.

Antwort1

Erweitern Sie einfach Ihren Ansatz:

exec 2> >(tee -a stderr stdall) 1> >(tee -a stdout stdall)

Der Standardfehler wird in die Datei mit dem Namen geschrieben stderr, die Standardausgabe in stdoutund sowohl der Standardfehler als auch die Standardausgabe werden auch in die Konsole geschrieben (oder worauf auch immer die beiden Dateideskriptoren zum Zeitpunkt execder Ausführung zeigen) und in stdall. (Anhängen) ist erforderlich, um ein Überschreiben durch den Sekundenzeiger zu
tee -averhindern , der mit dem Schreiben dorthin beginnt.stdalltee

Beachten Sie, dassdie Bestellungin denen Umleitungen durchgeführt werden, ist relevant: Die zweite Prozessersetzung wird von der ersten Umleitung beeinflusst, d. h. die von ihr ausgegebenen Fehler würden an gesendet >(tee -a stderr stdall). Sie können die Standardfehlerausgabe der zweiten Prozessersetzung natürlich an umleiten, um /dev/nulldiesen Nebeneffekt zu vermeiden. Eine Umleitung der Standardausgabe vor der Standardfehlerausgabe würde alle Fehler auch an stdoutund senden stdall.

Da die Befehle in Bashs Prozesssubstitutionen ausgeführt werdenasynchron, gibt es keine Garantie dafür, dass die Ausgabe in der Reihenfolge angezeigt wird, in der sie generiert wurde. Schlimmer noch: Fragmente der Standardausgabe und der Standardfehlerausgabe erscheinen wahrscheinlich in derselben Zeile.

Antwort2

Ihr Skript kann sich selbst vollständig ausführen $0(mit Festlegen und Überprüfen einer Umgebungsvariablen, um eine Endlosschleife zu vermeiden), anstatt sich auf > >(...)die Konstruktion von Bash zu verlassen, die laut IMLE kapriziös und unzuverlässig ist.

if [ "$REDIRECTED" != 1 ]; then
        export REDIRECTED=1
        set -o pipefail
        { { "$0" | tee stdout >&3; } 2>&1 | tee stderr; } 3>&1 | tee stdboth
        exit
fi
# rest of your script here

Da teekeine Zeilenpufferung verwendet (und dies auch nicht mit erzwungen werden kann stdbuf(1)), wird die Reihenfolge der in stdout und stderr geschriebenen Daten in der endgültigen Ausgabe nicht beachtet. Bei einem Befehl, der die vollständige Pufferung verwendet und sowohl in stdout als auch in stderr schreibt, hilft nicht einmal eine Zeilenpufferung, teeund schlimmer noch, Sie erhalten möglicherweise Ausgabezeilen, die zur Hälfte aus stdout und zur Hälfte aus stderr bestehen.

Ich glaube nicht, dass es dafür eine Lösung gibt, wenn man nur die Shell-Sprache und leicht verfügbare Befehlszeilen-Dienstprogramme verwendet.

Antwort3

Ich erstelle eine CI/CD-Bibliothek und weiß nicht, wofür die Clients die Bibliothek verwenden würden. Deshalb möchte ich jeden Anwendungsfall berücksichtigen.

Ich stelle die Notwendigkeit von Bash zur Verarbeitung der Ausgaben in Frage, da dies das Szenario ist. Idealerweise möchten Sie in diesem Zusammenhang die Ausgabe mit einem Zeitstempel versehen und ihr eine ID für den Standardausgabetyp zuweisen, und die Anwendung sollte diejenige sein, die entscheidet, was mit den Nachrichten zu tun ist.

verwandte Informationen