So leiten Sie die Ausgabe in mehrere Protokolldateien um

52

Wie leite ich die Standardausgabe in mehrere Protokolldateien um? Folgendes funktioniert nicht:

some_command 1> output_log_1 output_log_2 2>&1
Doppeldecker
quelle
6
Mit zshkönnen Sie verwenden some_command >output_log_1 >output_log_2.
Jofel

Antworten:

70

Siehe man tee:

NAME: tee - von der Standardeingabe lesen und in die Standardausgabe und Dateien schreiben

ÜBERSICHT: tee [OPTION] ... [DATEI] ...

Entsprechend:

echo test | tee file1 file2 file3
akond
quelle
Kann das stderr auch in mehr als einer Datei umgeleitet werden?
fromnaboo
Ja, dies kann durch Umleitung erfolgen: find / -name test 2> & 1 | tee datei1 datei2 datei3
seit dem
@akond, cmd 2>&1 | tee log1 log2 ich habe versucht, wie oben ausgeführt, aber ich muss Strg-C drücken, um es in die zweite Protokolldatei umzuleiten. Auch die Ausgabe wird auf der Konsole gedruckt. Ich möchte, dass die Befehlsausgabe in die Protokolle umgeleitet wird, aber nicht in die Konsole. Jede Hilfe wird gebeten.
Doppeldecker
@doubledecker Der teeBefehl schreibt stdinin Datei (en) und auch in stdout. Wenn Sie nicht möchten, dass die Ausgabe auf dem Terminal angezeigt wird, müssen Sie sie wie gewohnt umleiten /dev/null.
Minix
4
Es ist auch möglich, an mehrere Dateien anzuhängen:echo test | tee --append file1 file2
user1364368
13

Angenommen, Ihre Ausgabe wird aus einer Funktion generiert cmd():

cmd() {
    echo hello world!
}

Um die Ausgabe von cmdin zwei Dateien, aber nicht in die Konsole umzuleiten , können Sie Folgendes verwenden:

cmd | tee file1 file2 >/dev/null

Dies funktioniert für mehrere Dateien, vorausgesetzt, alle Datenquellen werden an tee weitergeleitet:

echo "foobarbaz" | tee file1 file2 file3 file4 > /dev/null

Dies wird auch funktionieren:

echo $(cmd) | tee file1 file2 >/dev/null

Ohne die /dev/nullUmleitung sendet tee zusätzlich zu den angegebenen Dateien eine Ausgabe an stdout .

Wenn dies beispielsweise über die Konsole ausgeführt wird, wird die Ausgabe dort angezeigt. Auf einer Crontab ausgeführt, wird in der Ausgabe die Statusmeldung angezeigt, die an Sie gesendet wurde (siehe auch Gilles 'Antwort hier https://unix.stackexchange.com/a/100833/3998 ).

Dies funktionierte für mich in Bash auf Ubuntu 12.04 und wurde in Ubuntu 14.04 mit GNU Bash 4.3.11 (1) verifiziert, so dass es auf jeder aktuellen GNU Bash-Version funktionieren sollte.

KP MacGregor
quelle
@doubledecker - dies scheint Ihre Bedingungen zu erfüllen und kann als Antwort akzeptiert werden. Außerdem +1, da ich dies unter GNU bash ( version 4.3.11(1)-release (i686-pc-linux-gnu)) in Ubuntu 14.04 getestet habe .
Belacqua
9

Es ist ein alter Beitrag, aber ich habe ihn gerade gefunden ...

Anstatt die Ausgabe an > /dev/nullumzuleiten, können Sie sie an die letzte Datei umleiten:

echo "foobarbaz" | tee file1 > file2

Oder zum Anhängen der Ausgabe:

echo "foobarbaz" | tee -a file1 >> file2
James Cook
quelle
Dies ist mehr oder weniger das, was andere Antwort sagte (außer -a in Abschlag)
Archemar
Dies ist der richtige Weg.
71GA
5

Wie @jofel in einem Kommentar unter der Antwort erwähnt hat, kann dies nativ erfolgen in zsh:

echo foobar >file1 >file2 >file3

oder mit Klammererweiterung:

echo foobar >file{1..3}

Intern funktioniert dies sehr ähnlich zu den oben angegebenen teeAntworten. Die Shell verbindet die Standardausgabe des Befehls mit einem Prozess, der an mehrere Dateien weiterleitet. Daher gibt es keinen zwingenden technischen Vorteil, wenn man es so macht (aber es sieht wirklich gut aus). Weitere Informationen finden Sie im zshHandbuch .

strugee
quelle
2

Ein anderer Ausdruck ist jedoch nicht möglich

echo "foobarbaz" | tee file1 file2 file3 file4 file5 file6 file7 file8 > /dev/null

Könnte vereinfacht werden, wenn es um viele Dateien geht.

echo "foobarbaz" | tee file{1..8} > /dev/null
user149146
quelle
2
Inwiefern unterscheidet sich das wirklich von den anderen bereits gegebenen Antworten? Zumal wahrscheinlich nur wenige Leute einen wörtlichen file1Durchgang file8als Namen wollen und dies wahrscheinlich nur beispielhafte Platzhalter für die Namen der Dateien sind
Eric Renouf,
1
Wahrscheinlich oder nicht, das ist genau die Lösung, die ich brauchte, und ich dachte, es könnte jemand anderem helfen.
user149146