2017-04-12 4 views
0

Ich habe einige Legacy bash Code, den ich ausführen und Druckanweisungen einfügen möchten, die auf stdout gehen sollte. Ich möchte alles, dass hätte gegangen, um zu stdout gehen zu out.out und alles, was hätte gegangen, um stderr zu gehen err.err.Redirect Ausgabe auf 3 verschiedene Dateien basierend auf Inhalt

myCode.sh 2> err.err 1> out.out Rennen wird alles aus als normal drucken, aber ich möchte in print-Anweisungen wie echo "NewStatement: I am at this point in the code" setzen und dann irgendwie vorge grep für NewStatement und an stdout zu senden, während alles andere als normal behandelt wird.

Im Grunde möchte ich mag:

1) alles in stdout senden NewStatement zu stdout

2) senden alles in stdout enthält nicht enthält NewStatement zu out.out

3) senden alles in stderr bis err.err

ist das möglich?

Antwort

0

Es ist sehr einfach. Zuerst die "Anfänger" -Lösung.

erstellen wrapper Skript (oder Wrapper-Funktion in Ihrem Haupt-Skript), die so etwas wie dies enthalten:

#!/bin/bash 

while read line || [[ $line ]] 
do 
    if 
    [[ $line =~ NewStatement ]] 
    then 
    echo "$line" 
    else 
    echo "$line" >> out.out 
    fi 
done< <("[email protected]" 2>err.err) 

dann einfach Ihr Skript wie folgt aufrufen (vorausgesetzt, alles ausführbar ist und im aktuellen Verzeichnis:

./wrapper myCode.sh 

Der Modus „Erweitert“ Lösung verwendet einen Dateideskriptor die Zieldatei zum Schreiben zu öffnen.

#!/bin/bash 

exec 3> out.out # Open file descriptor 3 for writing to file 

while read line || [[ $line ]] 
do 
    if 
    [[ $line =~ NewStatement ]] 
    then 
    echo "$line" 
    else 
    echo "$line" >> &3 
    fi 
done< <("[email protected]" 2>err.err) 

exec 3>&- # Close file descriptor 

Sie könnten viele Dateideskriptoren verwenden, um die Ausgabe in vielen separaten Dateien auf der Grundlage beliebiger komplexer Bedingungen auszuführen.

1

Sie können es wie folgt tun:

>out.out 

./myCode.sh 2> err.err 1> >(awk '!/^NewStatement/{print > "out.out"; next} 1') 

awk Befehl innerhalb Prozess Substitution druckt out.out wenn Linie mit NewStatement startet nicht. Andernfalls werden Zeilen beginnend mit NewStatement unter stdout gedruckt.

1

Alternativ können Sie

myCode.sh 2>err.err | tee >(grep -v NewStatement > out.out) | grep NewStatement 

Die tee dupliziert alles von seinem stdin, so

  • -T-ed Strom durch grep -v patt gefiltert wird (zB nicht enthalten) und umgeleitet
  • die stdout wenn gefiltert durch grep patt (znur Linien, wenn enthalten)

Dies kann beliebig oft wiederholt werden, wie

cmd | tee >(cmd1) >(cmd2) >(cmd3) | cmd 
Verwandte Themen